ubuntuusers.de

Python: Ohne wait() auf Beenden von subprocess warten

Status: Gelöst | Ubuntu-Version: Nicht spezifiziert
Antworten |

jan93

Anmeldungsdatum:
27. September 2007

Beiträge: 245

Wohnort: /home/jan

Ich starte mit folgendem Code in Python Timidity:

self.process = subprocess.Popen( ["timidity", self.filename], stdout=subprocess.PIPE, stderr=subprocess.STDOUT )


Nun möchte ich einen bestimmten Code ausführen, wenn Timidity beendet ist.
Wie bekomme ich das ohne wait() hin? Mit wait() hängt sich immer das Programm auf und die GUI wird grau (Compiz Fusion).

encbladexp Team-Icon

Ehemaliger
Avatar von encbladexp

Anmeldungsdatum:
16. Februar 2007

Beiträge: 17524

Wie wäre es mit einem extra Thread für timity?

mfg Betz Stefan

jan93

(Themenstarter)

Anmeldungsdatum:
27. September 2007

Beiträge: 245

Wohnort: /home/jan

Timidity ist jetzt in einem eigenen Thread, allerdings funktioniert die Stop-Funktion nicht mehr, weil die im gleichen Thread ist und ich jetzt für den subprocess wait() verwende.
Hier der Code: http://ubuntuusers.de/paste/211281/

jan93

(Themenstarter)

Anmeldungsdatum:
27. September 2007

Beiträge: 245

Wohnort: /home/jan

Ich habe es nun gelöst, indem ich in der while-Schleife des Midi-Threads mittels folgendem Code abfrage, ob Timidity schon beendet ist, statt mit wait() den Thread zu blockieren.

if hasattr(self, "process") and self.process.poll() != None and self.waiting == True:
	# Code ausführen
	self.waiting = False

Die Funktion PlayMidi sieht nun so aus:

def PlayMidi( self, **args ):
	self.StopMidi( True )
	print "Starte Timidity..."
	command = ["timidity", "--volume", args["volume"], "--adjust-tempo", args["tempo"], args["filename"] ]
	self.process = subprocess.Popen( command, stdout=subprocess.PIPE, stderr=subprocess.STDOUT )
	self.waiting = True

Lunar

Anmeldungsdatum:
17. März 2006

Beiträge: 5792

Diese Art des Pollings ist so ziemlich der schlechteste Weg, das zu lösen. Man verbrät nicht nur endlose CPU-Zyklen, sondern verhindert z.B. auch effektiv, dass sich der Kern in den Stromsparmodus versetzt. Mit solchem Polling kann man die Akkulaufzeit von Notebooks sehr effektiv verkürzen 😉

Hello_World

Anmeldungsdatum:
13. Juni 2006

Beiträge: 3620

Du solltest den Prozess in den Eventloop Deines Programms einbauen. Wie das genau geht, hängt m. W. vom verwendeten GUI-Toolkit ab, hier sind z. B. die entsprechenden Funktionen in PyGTK.
http://pygtk.org/docs/pygobject/gobject-functions.html#function-gobject--child-watch-add
http://pygtk.org/docs/pygobject/gobject-functions.html#function-gobject--io-add-watch

jan93

(Themenstarter)

Anmeldungsdatum:
27. September 2007

Beiträge: 245

Wohnort: /home/jan

Danke an euch beide, ich habe es jetzt mit wx.Process gemacht und kann mir so auch den extra Thread sparen.

Antworten |