Warum sind Python-Programme oft langsamer als das Äquivalent-Programm in C oder C ++ geschrieben?

Warum scheint Python im Durchschnitt langsamer als C / C ++? Ich habe Python als meine erste Programmiersprache gelernt, aber ich habe gerade erst mit C angefangen und schon fühle ich, dass ich einen deutlichen Unterschied sehen kann.

8 Solutions collect form web for “Warum sind Python-Programme oft langsamer als das Äquivalent-Programm in C oder C ++ geschrieben?”

Python ist eine höhere Sprache als C, was bedeutet, dass es die Details des Computers von Ihnen abstrakt – Speicherverwaltung, Zeiger usw., und ermöglicht es Ihnen, Programme in einer Weise zu schreiben, die näher ist, wie Menschen denken.

Es ist wahr, dass C-Code in der Regel läuft 10 bis 100 mal schneller als Python-Code, wenn Sie nur die Ausführungszeit zu messen. Allerdings, wenn Sie auch die Entwicklungszeit Python oft schlägt C. Für viele Projekte ist die Entwicklungszeit weitaus kritischer als die Laufzeit Leistung. Längere Entwicklungszeit verwandelt sich direkt in zusätzliche Kosten, weniger Features und langsamer auf den Markt.

Intern ist der Grund, warum Python-Code langsamer ausgeführt wird, weil Code zur Laufzeit interpretiert wird, anstatt bei der Kompilierzeit mit dem nativen Code kompiliert zu werden.

Andere interpretierte Sprachen wie Java-Bytecode und .NET-Bytecode laufen schneller als Python, da die Standardverteilungen einen JIT-Compiler enthalten , der Bytecode zum nativen Code zur Laufzeit kompiliert. Der Grund, warum CPython noch keinen JIT-Compiler hat, ist, weil die dynamische Natur von Python es schwierig macht, einen zu schreiben. Es gibt Arbeit im Gange , um eine schnellere Python-Laufzeit zu schreiben, so dass Sie erwarten sollten, dass die Performance-Lücke in der Zukunft reduziert wird, aber es wird wahrscheinlich eine Weile dauern, bis die Standard-Python-Distribution einen leistungsstarken JIT-Compiler enthält.

CPython ist besonders langsam, weil es keinen Just-in-Time-Optimierer hat (da es die Referenzimplementierung ist und in bestimmten Fällen die Einfachheit über die Leistung wählt). Unbeladen-Schwalbe ist ein Projekt, um ein LLVM-unterstütztes JIT in CPython hinzuzufügen und erreicht massive Beschleunigungen. Es ist möglich, dass Jython und IronPython viel schneller als CPython sind, sowie sie werden von stark optimierten virtuellen Maschinen (JVM und .NET CLR) unterstützt.

Eine Sache, die wohl Python langsamer verlassen wird, ist, dass es dynamisch typisiert ist, und es gibt Tonnen von Lookup für jeden Attribut Zugriff.

Zum Beispiel wird das Aufrufen von f auf ein Objekt A zu möglichen Lookups in __dict__ , ruft zu __getattr__ , etc, dann endlich __call__ auf dem aufrufbaren Objekt f .

In Bezug auf die dynamische Typisierung gibt es viele Optimierungen, die getan werden können, wenn Sie wissen, welche Art von Daten Sie zu tun haben. Zum Beispiel in Java oder C, wenn Sie eine gerade Reihe von Ganzzahlen haben, die Sie summieren möchten, kann der endgültige Assemblierungscode so einfach sein, wie den Wert am Index i holen, ihn dem accumulator hinzuzufügen und dann zu erhöhen.

In Python ist das sehr schwer, den Code so optimal zu machen. Sagen Sie haben eine Liste Unterklasse Objekt mit int s. Bevor man irgendwelche hinzufügt, muss Python list.__getitem__(i) , dann füge das zu dem "Akkumulator" hinzu, indem accumulator.__add__(n) , dann wiederhole. Tonnen von alternativen Lookups können hier passieren, weil ein anderer Thread zum Beispiel die __getitem__ Methode, das Dict der List-Instanz oder das Dict der Klasse geändert hat, zwischen Anrufen zum Hinzufügen oder Getitem. Sogar das Finden des Akkumulators und der Liste (und jede Variable, die Sie verwenden) im lokalen Namespace verursacht eine dict-Suche. Dieselbe Overhead gilt bei Verwendung eines benutzerdefinierten Objekts, obwohl es für einige eingebaute Typen etwas abgemildert ist.

Es ist auch erwähnenswert, dass die primitiven Typen wie bigint (int in Python 3, lang in Python 2.x), Liste, Set, Dict, etc, etc, sind, was die Leute viel in Python verwenden. Es gibt Tonnen von Operationen auf diesen Objekten, die bereits genug optimiert sind. Zum Beispiel, für das Beispiel oben, würden Sie nur sum(list) anstatt mit einem Akkumulator und Index. Anhängen an diese, und ein bisschen nummerieren mit int / float / complex, du wirst in der Regel keine schnellen Probleme haben, und wenn du es tust, gibt es wahrscheinlich eine kleine zeitkritische Einheit (zB eine SHA2-Digest-Funktion) Einfach ausziehen zu C (oder Java-Code, in Jython). Die Tatsache ist, dass, wenn Sie Code C oder C + +, werden Sie verschwenden viel Zeit, Dinge zu tun, die Sie in ein paar Sekunden / Zeilen von Python-Code tun können. Ich würde sagen, der Kompromiss ist immer wert, außer für Fälle, wo Sie etwas wie eingebettet oder Echtzeit-Programmierung machen und es sich nicht leisten können.

Der Unterschied zwischen python und c ist der übliche Unterschied zwischen einem interpretierten (Bytecode) und kompilierten (zu nativen) Sprache. Persönlich sehe ich nicht wirklich Python als langsam, es verwaltet es gut. Wenn du versuchst, es außerhalb seines Reiches zu benutzen, wird es natürlich langsamer. Aber dafür kannst du C-Erweiterungen für python schreiben, die zeitkritische Algorithmen in nativen Code setzen und damit schneller machen.

Kompilierung vs Interpretation ist hier nicht wichtig: Python ist kompiliert, und es ist ein kleiner Teil der Laufzeitkosten für alle nicht-trivialen Programm.

Die primären Kosten sind: das Fehlen eines ganzzahligen Typs, der nativen Ganzzahlen entspricht (wodurch alle ganzzahligen Operationen erheblich teurer werden), der Mangel an statischer Typisierung (was die Auflösung von Methoden erschwert und bedeutet, dass die Arten von Werten überprüft werden müssen Zur Laufzeit) und das Fehlen von ungekürzten Werten (die den Speicherverbrauch reduzieren und ein Niveau der Indirektion vermeiden können).

Nicht, dass irgendwelche dieser Dinge nicht möglich sind oder nicht effizienter in Python gemacht werden können, aber die Wahl wurde gemacht, um Programmierer Bequemlichkeit und Flexibilität zu bevorzugen, und Sprachreinheit über Laufzeitgeschwindigkeit. Einige dieser Kosten können durch eine kluge JIT-Kompilierung überwunden werden, aber die Vorteile, die Python bietet, werden immer zu einigen Kosten kommen.

Python wird typischerweise als Skriptsprache implementiert. Das heißt, es geht durch einen Dolmetscher, was bedeutet, dass es Code auf der Fliege in die Maschinensprache übersetzt, anstatt die ausführbare Datei in der Maschinensprache von Anfang an zu haben. Infolgedessen muss es die Kosten für das Übersetzen von Code zusätzlich zu dessen Ausführung bezahlen. Das gilt auch für CPython, obwohl es sich um einen Bytecode handelt, der näher an der Maschinensprache liegt und daher schneller übersetzt werden kann. Mit Python kommt auch einige sehr nützliche Laufzeit-Features wie dynamische Typisierung, aber solche Dinge können typischerweise auch bei den effizientesten Implementierungen ohne schwere Laufzeitkosten nicht implementiert werden.

Wenn Sie sehr prozessorintensive Arbeit wie das Schreiben von Shader machen, ist es nicht ungewöhnlich, dass Python irgendwo um 200 mal langsamer als C ++ ist. Wenn du CPython benutzt, kann diese Zeit halbiert werden, aber es ist immer noch nirgends so schnell wie möglich. Mit all diesen Runtmie Goodies kommt ein Preis. Es gibt viele Benchmarks, um dies zu zeigen und hier ist ein besonders gutes. Wie auf der Titelseite zugelassen, sind die Benchmarks fehlerhaft. Sie sind alle eingereicht von den Nutzern versuchen ihr Bestes, um effiziente Code in der Sprache ihrer Wahl zu schreiben, aber es gibt Ihnen eine gute allgemeine Idee.

Ich empfehle Ihnen, die beiden zusammen zu mischen, wenn Sie sich um Effizienz kümmern: Dann können Sie das Beste aus beiden Welten bekommen. Ich bin in erster Linie ein C ++ – Programmierer, aber ich denke, eine Menge Leute neigen dazu, zu viel von der banalen, High-Level-Code in C + + Code, wenn es nur ein Ärgernis zu tun ist (kompilieren Zeiten als nur ein Beispiel). Das Mischen einer Skriptsprache mit einer effizienten Sprache wie C / C ++, die näher am Metall ist, ist wirklich der Weg, um die Effizienz der Effizienz (Produktivität) mit der Effizienz der Verarbeitung zu erhöhen.

Der Vergleich von C / C ++ mit Python ist kein fairer Vergleich. Wie beim Vergleich eines F1 Rennwagens mit einem Nutzfahrzeug.

Was überrascht ist, wie schnell Python im Vergleich zu seinen Kollegen anderer dynamischer Sprachen ist. Während die Methodik oft als fehlerhaft betrachtet wird, schau dir das Computer-Sprach-Benchmark-Spiel an, um die relative Sprachgeschwindigkeit auf ähnlichen Algorithmen zu sehen.

Der Vergleich zu Perl, Ruby und C # sind mehr "fair"

C und C ++ kompilieren auf nativen Code – das heißt, sie laufen direkt auf der CPU. Python ist eine interpretierte Sprache, was bedeutet, dass der Python-Code, den du schreibst, durch viele, viele Stufen der Abstraktion gehen muss, bevor er ausführbarer Maschinencode werden kann.

Anders als die bereits gebuchten Antworten, ist eine Sache Pythons Fähigkeit, die Dinge in der Laufzeit zu ändern, die Sie nicht ändern können in Beispiel C. Sie können Mitgliedsfunktionen zu Klassen hinzufügen, wie Sie gehen. Auch pythons dynamische Natur macht es unmöglich zu sagen, welche Art von Parametern an eine Funktion übergeben werden, was wiederum die Optimierung einer ganzen Menge härter macht.

RPython scheint ein Weg zu sein, das Optimierungsproblem zu umgehen .

Dennoch wird es wahrscheinlich nicht in der Nähe der Leistung von C für das Zahlencrunch und dergleichen sein.

Python ist die beste Programmiersprache der Welt.