Seite 1 von 1
multiprocessing und class
Verfasst: Freitag 6. März 2015, 10:39
von Pookie
Hallöchen,
also mein Problem besteht darin, dass ich im endeffekt eine Methode einer Klasse per multiprocessing nutzen will und das einfach ohne Fehlermeldung nicht funktioniert (d.h. es kommt wirklich keine Fehlermeldung es macht einfach irgendwas, aber nicht was es soll). Der Code für das multiprocessing mit einer "normalen" Funktion außerhalb einer Klasse funktioniert. Im Prinzip sieht der Code so aus wie unten, das soll auch wirklich nur das Prinzip darstellen. Mein Ziel wäre den unteren Teil auch noch irgendwie auszulagern aber das funktioniert dann genauso wenig. Ich würde halt gern das "zu berechnende Problem" und die methoden, welche es dann zb für gewisse parameter lösen irgendwie trennen damit alles nicht zu unübersichtlich wird. Eventuell gibt es da ja auch bessere Ansätze.
Code: Alles auswählen
# das sind die module die ich im original nutze
from numpy import *
from scipy.integrate import odeint
from multiprocessing import Pool
class bla:
def a(x):
macht was
def b(x,y):
return 2*a(x) # im sinne das hier methode b auch wirklich nochmal methode a intern nutzt
result = []
def callback_func(x):
result.append(x)
def multi():
pool = Pool(4)
for i in linspace(1,2,3):
pool.apply_async(blabla.b,args=(i,0,),callback=callback_func)
pool.close()
pool.join()
print(sorted(result))
blabla = bla()
multi()
Re: multiprocessing und class
Verfasst: Freitag 6. März 2015, 11:06
von MagBen
So geht's
Code: Alles auswählen
from numpy import *
from scipy.integrate import odeint
from multiprocessing import Pool
class bla:
def a(self, x):
return 1.1*x
def __call__(self, x,y):
return 2*self.a(x) # im sinne das hier methode b auch wirklich nochmal methode a intern nutzt
result = []
def callback_func(x):
result.append(x)
def multi():
pool = Pool(4)
for i in linspace(1,2,3):
pool.apply_async(blabla,args=(i,0),callback=callback_func)
pool.close()
pool.join()
print(sorted(result))
blabla = bla()
multi()
und hier steht warum:
http://stackoverflow.com/questions/1816 ... ng-pool-ma
Re: multiprocessing und class
Verfasst: Freitag 6. März 2015, 11:46
von Pookie
Ich muss gestehen, dass die Variante bei mir nicht funktioniert. Ich hab mir auch mal den Link angeschaut und versucht
You could also define a __call__() method inside your someClass(), which calls someClass.go() and then pass an instance of someClass() to the pool. This object is pickleable and it works fine (for me)...
umzusetzen (was ja fast deine Variante ist) jedoch auch ohne Erfolg, wenngleich das wohl eher an meinem Unvermögen liegen wird :K
Re: multiprocessing und class
Verfasst: Freitag 6. März 2015, 11:56
von MagBen
Pookie hat geschrieben:Ich muss gestehen, dass die Variante bei mir nicht funktioniert.
Hast Du meinen Code komplett kopiert und ausprobiert oder hast Du in Deinem Code die Methode b durch __call__ ersetzt? (Es gab in Deinem Code nämlich noch mehr Fehler.)
Re: multiprocessing und class
Verfasst: Freitag 6. März 2015, 12:00
von EyDu
Hallo und willkommen im Forum!
"Funktioniert nicht" ist etwas unspezifisch und wenig hilfreich für uns. Was genau funktioniert denn nicht? Gibt es eine Fehlermeldung? Fackelt der PC ab? Bellt dein Hund? Du müsstest da schon etwas spezifischer werden: Was genau funktioniert nicht, wie wirkt sich das aus. Gibt es eine Fehlermeldung? Was besagt die und wie lautet der Traceback dazu?
*-Importe solltest du dir bei der Gelegenheit gleich abgewöhnen, die machen ein Programm nur unleserlich, unübersichtlich und die Herkunft von Namen nur schwer nachvollziehbar. Im schlimmsten Fall überschreibst du dir versehentlich andere Namen. Gerade bei numpy ist ein *-Import keine gute Idee, das füllt den gesamten Namensraum um über 500 Werte an.
Re: multiprocessing und class
Verfasst: Freitag 6. März 2015, 13:11
von BlackJack
Man sollte auch die ganzen Programmierrichtlinien aus der Dokumentation befolgen. Zum Beispiel das das Hauptmodul nebeneffektfrei importiert werden können muss ist zwar nur für Windows zwingend notwendig bei `multiprocessing`, aber generell für jedes Modul eine gute Idee.
Re: multiprocessing und class
Verfasst: Samstag 7. März 2015, 09:52
von Pookie
Erstmal danke für die Antworten, ich versuche da mal alles etwas zu spezifizieren. Zunächst nutze ich das fertige Packet Anaconda mit Python 3.4 auf Win-64-bit. Als IDE nutze ich Spyder, welche bei Anaconda mit dabei ist und dort führe ich das Programm in einer IPython console aus.
MagBen hat geschrieben:Hast Du meinen Code komplett kopiert und ausprobiert oder hast Du in Deinem Code die Methode b durch __call__ ersetzt? (Es gab in Deinem Code nämlich noch mehr Fehler.)
Sowohl als auch. Mein Code hier war auch nur eine "Skizze" und mein originaler Code sollte keine so offensichtlichen Fehler enthalten. Aber auch komplett kopiert funktioniert es nicht.
Das komische ist einfach, dass wirklich keine Fehlermeldung aufkommt... als ich das schrieb kam mir die Idee anstatt der IPython mal die normale Python console zu nutzen und dort kam doch ein Fehler:
Der Traceback is relativ länglich
File "F:\Anaconda3\lib\multiprocessing\spawn.py", line 137, in _check_not_importing_main
is not going to be frozen to produce an executable.''')
RuntimeError:
An attempt has been made to start a new process before the
current process has finished its bootstrapping phase.
This probably means that you are not using fork to start your
child processes 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 an executable.
Ausgeführt wurde dieser Code in o.g. Umgebung:
Code: Alles auswählen
from numpy import linspace
from multiprocessing import Pool
class bla:
def a(self, x):
return 1.1*x
def __call__(self, x,y):
return 2*self.a(x) # im sinne das hier methode b auch wirklich nochmal methode a intern nutzt
result = []
def callback_func(x):
result.append(x)
def multi():
pool = Pool(4)
for i in linspace(1,2,3):
pool.apply_async(blabla,args=(i,0),callback=callback_func)
pool.close()
pool.join()
print(sorted(result))
blabla = bla()
multi()
EDIT:
Da ich den Fehler echt erst beim schreiben des Posts gefunen habe, habe ich erstmal abgeschickt. Aber nun nach ein wenig google bin ich auf:
Code: Alles auswählen
from numpy import linspace
from multiprocessing import Pool
class bla:
def a(self, x):
return 1.1*x
def __call__(self, x,y):
return 2*self.a(x) # im sinne das hier methode b auch wirklich nochmal methode a intern nutzt
result = []
def callback_func(x):
result.append(x)
def multi():
pool = Pool(4)
for i in linspace(1,2,3):
pool.apply_async(blabla,args=(i,0),callback=callback_func)
pool.close()
pool.join()
print(sorted(result))
if __name__ == '__main__':
blabla = bla()
multi()
gekommen was sogar funktioniert.