Start Programmierung Python Python in einfachen Beispielen : Threads verstehen
20 | 05 | 2012
Python in einfachen Beispielen : Threads verstehen
Geschrieben von: Joerg   
Dienstag, den 03. Mai 2011 um 12:27 Uhr

Es wird bei modernen Betriebssystemen zwischen Prozessen und Tasks unterschieden. Ein Prozess ist ein Programm, welches abläuft. Prozesse laufen häufig "parallel" zueinander ab. Jeder Prozess hat in der Regel seinen eigenen Speicherraum. Eine Task ist ein Teil eines Prozesses. Gegenüber einem Prozess hat eine Task (Aufgabe) den gleichen Speicherraum, ansonsten ist das Verhalten ähnlich. Informationen der einen Task kann von einer anderen Task genutzt werden. Tasks werden in Python als Threads (übersetzt: Fäden) bezeichnet.

An irgendeiner Stelle kommt man um Threads nicht mehr herum. Beispielsweise, wenn wir mit einer grafischen Oberfläche arbeiten (Tkinter). Durch ein ButtonClick könnte ein Unterprogramm aufgerufen werden, in dem eine Endlosschleife vorhanden ist. Das Problem: sind wir erst einmal in der Endlosschleife, kommen wir nicht mehr heraus.

Das Python-Modul zum Thema Threads heißt threading.

Beispiel 1:

 

 

Python - Multitasking mit Threads
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
import threading, time
 
 
zaehler1=0
zaehler2=0
 
def Thread1():
global zaehler1
print "Starte Unterprogramm Thread1." 
while 1:
time.sleep(20)
zaehler1=zaehler1+1
print  "Thread 1: zaehler=", zaehler1 
print "Thread1"
 
def Thread2():
global zaehler1, zaehler2
print "Starte Unterprogramm Thread2." 
while 1:
time.sleep(10)
zaehler2=zaehler2+1
print "Thread 2: zaehler=", zaehler2 
print "Differenz der beiden Zaehler=",zaehler2-zaehler1 
print "Thread2" 
 
th1=threading.Thread(target=Thread1)
th2=threading.Thread(target=Thread2)
 
print "Th1 ist aktiv: ", th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."
 
th1.start()
 
print "Th1 ist aktiv: ", th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."
 
th2.start()
 
print 'Th1 ist aktiv: ', th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."

Was passiert?

Ich habe das Programm über eine kleine Batchdatei gestartet. Die Batchdatei liegt in dem Verzeichnis mit dem Skript Beispiel1.py. Klicke ich die Batchdatei an, so wird das Befehlsfenster des Programms cmd.exe geöffnet und das Skript wird von Python ausgeführt. Thread1 und Thread2 sind die beiden Unterprogramme, die parallel ablaufen sollen. Beide Unterprogramme enthalten eine Endlosschleife. Das Unterprogramm Thread2 benutzt über zaehler1 Informationen aus Thread1 (globale Variablen).

In den Zeile 37 und 38 werden Instanzen der Objektklasse Thread gebildet. Mit den Methoden isAlive, active_count erhalten wir allgemeine Statusmeldungen zu den Threads. Mit der Methode start wird ein Thread ausgeführt. Eine Methode stop gibt es nicht.  Die Ausgabe nach dem Start der Batch-Datei:

 

Threads1

Beispiel 2:

 

 

Python - Thread Beispiel 2
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
import threading, time
 
 
zaehler1=0
zaehler2=0
 
Th1_aktiv=True #Flag, um Schleife in Thread1 zu beenden
Th2_aktiv=True # Hier für Thread2 ...
 
def Thread1():
global zaehler1, Th1_aktiv
print "Starte Unterprogramm Thread1." 
while Th1_aktiv:
time.sleep(20)
zaehler1=zaehler1+1
print  "Thread 1: zaehler=", zaehler1 
print "Thread1" 
 
def Thread2():
global zaehler1, zaehler2, Th2_aktiv
print "Starte Unterprogramm Thread2." 
while Th2_aktiv:
time.sleep(10)
zaehler2=zaehler2+1
print  "Thread 2: zaehler=", zaehler2 
print  "Differenz der beiden Zaehler=",zaehler2-zaehler1 
print "Thread2"
 
th1=threading.Thread(target=Thread1)
th2=threading.Thread(target=Thread2)
 
 
print "Th1 ist aktiv: ", th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."
 
th1.start()
 
print "Th1 ist aktiv: ", th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."
 
th2.start()
 
print "Th1 ist aktiv: ", th1.isAlive()
print "Th2 ist aktiv: ", th2.isAlive()
print "Insgesamt sind ", threading.active_count(), " Threads aktiv."

 

Was passiert?

Wurde das Skript im Befehlsfenster gestartet, so können wir jetzt mit Th2_aktiv=False, den Thread Thread2 beenden.  Ich habe mit time.sleep(Zeit in Sekunden) die Ausgabe der Threads verlangsamt. Nach der Änderung von Th2_aktiv wird nur noch das Unterprogramm Thread1 ausgeführt und es besteht weiterhin die Eingabemöglichkeit von Kommandos in das Kommandofenster. Geben wir jetzt die Anweisung threading.active_count() ein, so werden jetzt zwei aktive Threads angezeigt. Geben wir T2_aktiv=True auf der Kommandoebene ein, so ändert sich an der Ausgabe nichts. Die Eingabe von th2.start() führt zu der Fehlermeldung, dass ein Thread nur einmal gestartet werden dürfe. Geben wir Thread2() ein, so werden wieder regelmäßig die beiden Threads ausgeführt, allerdings besteht jetzt die Kommandoeingabemöglichkeit nicht mehr.

 

 

Quellen:

http://docs.python.org/library/threading.html

http://de.wikipedia.org/wiki/Thread

http://wiki.python.de/Threading

http://www.hsg-kl.de/faecher/inf/python/thread/index.php

 

Tags: