Estou tentando meu primeiro programa python formal usando Threading e Multiprocessamento em uma máquina Windows. Não consigo iniciar os processos, porém, com python apresentando a seguinte mensagem. O fato é que não estou lançando meus threads no módulo principal . Os threads são tratados em um módulo separado dentro de uma classe.
EDIT : A propósito, este código funciona bem no Ubuntu. Não é bem no windows
RuntimeError:
Attempt to start a new process before the current process
has finished its bootstrapping phase.
This probably means that you are on Windows and you have
forgotten to use the proper idiom in the main module:
if __name__ == '__main__':
freeze_support()
...
The "freeze_support()" line can be omitted if the program
is not going to be frozen to produce a Windows executable.
Meu código original é bem longo, mas consegui reproduzir o erro em uma versão resumida do código. Ele é dividido em dois arquivos, o primeiro é o módulo principal e faz muito pouco além de importar o módulo que lida com processos / threads e chama um método. O segundo módulo é onde está a carne do código.
testMain.py:
import parallelTestModule
extractor = parallelTestModule.ParallelExtractor()
extractor.runInParallel(numProcesses=2, numThreads=4)
parallelTestModule.py:
import multiprocessing
from multiprocessing import Process
import threading
class ThreadRunner(threading.Thread):
""" This class represents a single instance of a running thread"""
def __init__(self, name):
threading.Thread.__init__(self)
self.name = name
def run(self):
print self.name,'\n'
class ProcessRunner:
""" This class represents a single instance of a running process """
def runp(self, pid, numThreads):
mythreads = []
for tid in range(numThreads):
name = "Proc-"+str(pid)+"-Thread-"+str(tid)
th = ThreadRunner(name)
mythreads.append(th)
for i in mythreads:
i.start()
for i in mythreads:
i.join()
class ParallelExtractor:
def runInParallel(self, numProcesses, numThreads):
myprocs = []
prunner = ProcessRunner()
for pid in range(numProcesses):
pr = Process(target=prunner.runp, args=(pid, numThreads))
myprocs.append(pr)
# if __name__ == 'parallelTestModule': #This didnt work
# if __name__ == '__main__': #This obviously doesnt work
# multiprocessing.freeze_support() #added after seeing error to no avail
for i in myprocs:
i.start()
for i in myprocs:
i.join()
python
windows
multiprocessing
NG Algo
fonte
fonte
Respostas:
No Windows, os subprocessos irão importar (ou seja, executar) o módulo principal no início. Você precisa inserir uma
if __name__ == '__main__':
proteção no módulo principal para evitar a criação de subprocessos recursivamente.Modificado
testMain.py
:fonte
Tente colocar seu código dentro de uma função principal em testMain.py
Veja a documentação :
que dizem
... usando
if __name__ == '__main__'
fonte
Embora as respostas anteriores estejam corretas, há uma pequena complicação que ajudaria a comentar.
No caso de seu módulo principal importar outro módulo no qual variáveis globais ou variáveis de membro de classe são definidas e inicializadas para (ou usando) alguns novos objetos, você pode ter que condicionar essa importação da mesma maneira:
fonte
Como @Ofer disse, quando você estiver usando outras bibliotecas ou módulos, você deve importar todos eles dentro do
if __name__ == '__main__':
Então, no meu caso, acabou assim:
fonte
No meu caso foi um bug simples no código, usando uma variável antes de ser criada. Vale a pena verificar isso antes de tentar as soluções acima. Por que recebi essa mensagem de erro específica, o Senhor sabe.
fonte