MultiProcessing
- Multiprocessing fügt CPUs hinzu, um die Rechenleistung zu erhöhen.
- Mehrere Prozesse werden gleichzeitig ausgeführt.
- Die Erstellung eines Prozesses ist zeitaufwendig und ressourcenintensiv.
- Multiprocessing kann symmetrisch oder asymmetrisch sein.
- Die Multiprocessing-Bibliothek in Python verwendet separaten Speicherplatz, mehrere CPU-Kerne, umgeht die GIL-Beschränkungen in CPython, child Prozesse sind killbar (z. B. Funktionsaufrufe im Programm) und ist viel einfacher zu verwenden.
- Einige Fallstricke des Moduls sind ein größeres Speicher-Footprint und IPCs ein wenig komplizierter mit mehr Overhead.
Multithreading
- Multithreading erstellt mehrere Threads eines einzigen Prozesses, um die Rechenleistung zu erhöhen.
- Mehrere Threads eines einzigen Prozesses werden gleichzeitig ausgeführt.
- Die Erstellung eines Threads ist sowohl zeit- als auch ressourcenschonend.
- Die Multithreading-Bibliothek ist schlank, teilt den Speicher, ist verantwortlich für reaktives UI und wird gut für an I/O gebundene Anwendungen genutzt.
- Das Modul ist nicht killbar und unterliegt der GIL.
- Mehrere Threads leben im selben Prozess im selben Bereich, jeder Thread wird eine spezifische Aufgabe erledigen, hat seinen eigenen Code, eigenen Stack-Speicher, Befehlszeiger und teilt den Heap-Speicher.
- Wenn ein Thread ein Speicherleck hat, kann er die anderen Threads und den übergeordneten Prozess beschädigen.
Beispiel für Multi-Thread und Multi-Processing mit Python
Python 3 hat die Möglichkeit, parallele Aufgaben zu starten. Das erleichtert unsere Arbeit.
Es hat für Thread-Pooling und Process-Pooling.
Das Folgende gibt einen Einblick:
ThreadPoolExecutor Beispiel
import concurrent.futures
import urllib.request
URLS = ['http://www.foxnews.com/',
'http://www.cnn.com/',
'http://europe.wsj.com/',
'http://www.bbc.co.uk/',
'http://some-made-up-domain.com/']
# Eine einzelne Seite abrufen und die URL sowie den Inhalt melden
def load_url(url, timeout):
with urllib.request.urlopen(url, timeout=timeout) as conn:
return conn.read()
# Wir können ein with-Statement verwenden, um sicherzustellen, dass Threads schnell aufgeräumt werden
with concurrent.futures.ThreadPoolExecutor(max_workers=5) as executor:
# Starten Sie die Ladevorgänge und markieren Sie jeden Future mit seiner URL
future_to_url = {executor.submit(load_url, url, 60): url for url in URLS}
for future in concurrent.futures.as_completed(future_to_url):
url = future_to_url[future]
try:
data = future.result()
except Exception as exc:
print('%r hat eine Ausnahme erzeugt: %s' % (url, exc))
else:
print('%r Seite hat %d Bytes' % (url, len(data)))
ProcessPoolExecutor Beispiel
import concurrent.futures
import math
PRIMES = [
112272535095293,
112582705942171,
112272535095293,
115280095190773,
115797848077099,
1099726899285419]
def is_prime(n):
if n % 2 == 0:
return False
sqrt_n = int(math.floor(math.sqrt(n)))
for i in range(3, sqrt_n + 1, 2):
if n % i == 0:
return False
return True
def main():
with concurrent.futures.ProcessPoolExecutor() as executor:
for number, prime in zip(PRIMES, executor.map(is_prime, PRIMES)):
print('%d ist eine Primzahl: %s' % (number, prime))
if __name__ == '__main__':
main()
9 Stimmen
Ich denke, das könnte im Allgemeinen nützlich sein: blogs.datalogics.com/2013/09/25/… Obwohl je nach Sprache interessante Dinge passieren können. Zum Beispiel sind laut Andrew Sledges Link die Python-Threads langsamer. Bei Java ist es genau umgekehrt, Java-Prozesse sind viel langsamer als Threads, weil für einen neuen Prozess eine neue JVM benötigt wird.
7 Stimmen
Keine der beiden Top-Antworten (aktuelle Top, zweite Antwort) behandelt das GIL in irgendeiner signifikanten Weise. Hier ist eine Antwort, die das GIL-Aspekt behandelt: stackoverflow.com/a/18114882/52074
0 Stimmen
@AndrasDeak können wir das umgekehrt schließen gemäß: meta.stackoverflow.com/questions/251938/…, da diese viel mehr Upvotes/Antworten hat?
3 Stimmen
@CiroSantilli der Grund, warum ich diese Richtung gewählt habe, ist, weil die Antworten auf diese Frage schrecklich sind. Die akzeptierte Antwort hat wenig Substanz, im Kontext von Python ist sie inakzeptabel. Die am meisten gevotete Antwort ist besser, aber es fehlt immer noch eine ordentliche Erklärung. Die akzeptierte Antwort des Duplikats hat eine ausführliche Erklärung von einem der besten Beitragenden (und Lehrer) im Tag, der tatsächlich erklärt, was die "GIL-Beschränkungen" sind und warum man entweder verwenden möchte. Ich würde es vorziehen, das Duplikat in dieser Richtung zu behalten. Ich glaube, wir haben darüber im Python Chat diskutiert, aber ich kann dort nach Meinungen fragen, wenn du möchtest.
0 Stimmen
Besonders, da nicht registrierte Benutzer von der doppelten Quelle zum Ziel umgeleitet werden, würde ich es hassen, wenn sie diesen Beitrag anstelle von abarnerts Antwort finden würden.
0 Stimmen
@AndrasDeak OK, ich werde meine Antwort dann kopieren, da sie die beste ist XD
2 Stimmen
@CiroSantilli ah, ich habe übersehen, dass du hier eine Antwort hast! Als ich sagte "die Antworten [...] sind schrecklich", habe ich natürlich die Anwesenden ausgeschlossen ;) Ich denke, es wäre viel besser, dort deine Antwort zu haben!