Multiprocessing

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
saihttam68
User
Beiträge: 2
Registriert: Dienstag 15. Januar 2013, 18:21

Hallo zusammen,

ich möchte gerne ein Programm erstellen das "würfelt " d.h. die Zahlen von 1-6 zufällig erzeugt und auf alle CPU-Kerne verteilen.

Habe ein bißchen mit multiprocessing getestet, allerdings erzeuge ich nur verschieden Prozesse, die seperat laufen. Eigentlich sollte nur die Berechnung auf alle CPU-Kern verteilt werden.

Bin für jeden Tip dankbar, anbei mein Programm

Code: Alles auswählen

import multiprocessing
import random

def worker():
    random.seed
    eins = 0
    zwei = 0
    drei = 0
    vier = 0
    fünf = 0
    sechs = 0

    for i in range (1,5000000): 
        a = random.randint(1,6)
    
        if a == 1:
            eins = eins + 1

        if a == 2:
            zwei = zwei + 1       

        if a == 3:
            drei = drei + 1

        if a == 4:
            vier = vier + 1

        if a == 5:
            fünf = fünf + 1

        if a == 6:
            sechs = sechs + 1

       
    print  (" Anzahl der Einsen: ", eins)
    print  (" Anzahl der Zweien: ", zwei)
    print  (" Anzahl der Dreien: ", drei)
    print  (" Anzahl der Vieren: ", vier)
    print  (" Anzahl der Fünfen: ", fünf)
    print  (" Anzahl der Sechsen: ", sechs)
    return

if __name__ == '__main__':
    jobs = []
    for i in range(5):
        p = multiprocessing.Process(target=worker())
        jobs.append(p)
        p.start()   


### Ausgabe ##########################
Anzahl der Einsen: 832077
Anzahl der Zweien: 832354
Anzahl der Dreien: 833209
Anzahl der Vieren: 835233
Anzahl der Fünfen: 833299
Anzahl der Sechsen: 833827
Anzahl der Einsen: 834705
Anzahl der Zweien: 832561
Anzahl der Dreien: 833484
Anzahl der Vieren: 832953
Anzahl der Fünfen: 834037
Anzahl der Sechsen: 832259
Anzahl der Einsen: 833688
Anzahl der Zweien: 834621
Anzahl der Dreien: 833693
Anzahl der Vieren: 834607
Anzahl der Fünfen: 831168
Anzahl der Sechsen: 832222
Anzahl der Einsen: 832716
Anzahl der Zweien: 832509
Anzahl der Dreien: 833393
Anzahl der Vieren: 834236
Anzahl der Fünfen: 835425
Anzahl der Sechsen: 831720
Anzahl der Einsen: 832293
Anzahl der Zweien: 833389
Anzahl der Dreien: 833050
Anzahl der Vieren: 832782
Anzahl der Fünfen: 833247
Anzahl der Sechsen: 835238

Danke und viele Grüße von Saihttam
BlackJack

@saihttam68: Die Prozesse sollte Dein Betriebssystem von sich aus auf die Kerne verteilen.

Das ``random.seed`` ist in zweierlei Hinsicht sinnfrei. Zum einen rufst Du es gar nicht auf, es halt also keinen Effekt, zum anderen würde selbst das Aufrufen keinen Sinn machen. Im Gegenteil können unter bestimmten Umständen die Zahlenfolgen dadurch sogar *weniger* zufällig werden.

Statt der Namen für die einzelnen Augenzahlen währe eine Liste oder ein Wörterbuch vernünftiger. Oder gleich `collections.Counter`.

Ein nacktes ``return`` am Ende einer Funktion macht keinen Sinn.

Statt jeden Worker einzeln *seine* Ergebnisse ausgeben zu lassen würde es vielleicht mehr Sinn machen die Ergebnisse von allen zu sammeln. Hier wäre vielleicht auch ein `multiprocessing.Pool` praktischer als die Anzahl der Worker selber festzulegen.

Interessant dass das auch bis zu ende läuft. Ich hätte trotzdem ein Warten auf alle Worker eingebaut.
saihttam68
User
Beiträge: 2
Registriert: Dienstag 15. Januar 2013, 18:21

Hallo BlackJack,

Danke für deine schnelle Antwort.

Mein Sohn sollte für den Matheunterricht 500x Würfeln, um das nicht per Hand zu machen, habe ich ein kleines
Programm geschrieben, so der Hintergrund.
Wir haben dann mehrere Durchläufe gemacht bis 5Mrd., das hat auf einem i5 QuadCore 6h gedauert.
Dabei habe ich gesehen, dass nur ein CPU-Kern genutzt wird. Ich habe auch immer gedacht,
das regelt das Betriebssystem ... es lief alles unter Windows7 64-bit. Dann habe ich das ganze unter Mac
OSX ML ausprobiert, identisches Verhalten, nur ein Kern wird verwendet ....
Aus diesem Grund bin ich dann zu Multiprocessing gekommen, Ziel soll sein das eine Berechnung läuft,
die alle vier Kerne nutzt. ist das überhaupt mit dem Modul multiprocessing möglich?

Deine Hinweis schaue ich mir noch mal an, habe seit Jahren nichts mehr programmiert, aber werde jetzt wieder
anfangen ;-)

Viele Grüße,
Saihttam
BlackJack

@saihttam68: Prozesse werden vom Betriebssystem üblicherweise auf verschiedene Prozessoren/Kerne verteilt wenn sie gleichzeitig laufen.

Ich sehe aber gerade das Du einen Fehler hast: Du musst als `target` die Funktion übergeben. Du rufst die Funktion aber auf und übergibst den Rückgabewert, in diesem Fall `None`, als `target`. Damit laufen Deine Worker alle nacheinander in einem Prozess, statt parallel in mehreren Prozessen. Das erklärt dann wahrscheinlich auch warum Dein Programm tatsächlich durchläuft obwohl Du nicht auf die Ergebnisse der Prozesse wartest.
Antworten