Ich kann verstehen, dass Java sowohl einen Compiler als auch einen Interpreter benötigt.
Das tut es nicht. In der Java-Sprachspezifikation gibt es nichts, was besagt, dass Java einen Compiler haben muss. Es gibt auch nichts in der Java-Sprachspezifikation, was besagt, dass Java einen Interpreter haben muss.
Ob ein Interpreter, ein Compiler oder eine Kombination aus beiden verwendet wird, liegt ganz im Ermessen des Implementierers.
Tatsächlich gibt es Implementierungen von Java, die direkt in Maschinencode kompiliert werden, z. B. den GNU Compiler für Java gcj
. Technisch gesehen kompiliert der Oracle OpenJDK Java-Compiler auch zu Maschinencode, insbesondere JVM-Bytecode. Nun, könnte man sagen, warte eine Minute, das ist kein Maschinencode! Es gibt jedoch Software-Interpreter für x86-Maschinencode und Hardware-CPUs, die JVM-Bytecode ausführen können. Was macht also einen "nativ" und den anderen nicht?
Beachten Sie, dass sich der JVM-Bytecode außerhalb der Java-Sprachspezifikation befindet, genau wie der x86-Maschinencode.
und dann übersetzt eine virtuelle Maschine (unter Windows, Linux, Android usw.) diesen Bytecode in Maschinencode für die aktuelle Architektur.
Auch dies liegt ganz beim Implementierer.
Die ursprüngliche Sun JVM wurde nie übersetzt, sondern immer interpretiert. Die aktuellen Oracle OpenJDK JVM-Interpretationen und nur die Teile, die häufig ausgeführt werden, werden kompiliert. Die Maxine Research VM wird immer JIT kompiliert. Die Implementierung von Excelsior.JET wird vorab einmal kompiliert. Die IKVM.NET-JVM wird in CIL-Bytecode kompiliert. Die Android Runtime wird einmal vor der Installation kompiliert. (Außerdem versteht die Android Runtime den JVM-Bytecode nicht, sondern verwendet Dalvik-Bytecode, eine völlig andere Sprache.)
Aber warum braucht Python sowohl einen Compiler als auch einen Interpreter?
Wieder nicht. In der Python-Sprachspezifikation gibt es nichts, was besagt, dass Python einen Compiler haben muss. Die Python-Sprachspezifikation enthält auch nichts, was besagt, dass Python einen Interpreter haben muss.
Beachten Sie, dass Python eigentlich nie interpretiert wird. Alle vorhandenen Python-Implementierungen kompilieren Python immer in eine andere Sprache. Diese Sprache kann dann wiederum interpretiert werden oder nicht, aber diese Sprache ist eine andere Sprache als Python. Python wird nicht interpretiert.
Warum nicht einfach Interpretation verwenden?
Weil Python nicht so konzipiert ist, dass es von Maschinen leicht interpretiert werden kann. Es ist so konzipiert, dass es vom Menschen leicht interpretiert werden kann. OTOH, CPython-Bytecode, ist so konzipiert, dass er von Maschinen leicht interpretiert werden kann. Es ist also sinnvoll , Code in einer für Menschen entwickelten Sprache zu schreiben und in einer für Maschinen entwickelten Sprache zu interpretieren. Um von einer zur anderen zu gelangen, müssen Sie kompilieren.
Soweit ich weiß, können Sie ein Python-Programm (zu Bytecode kompiliert) auf keinem Windows- oder Linux-Computer ohne Änderungen ausführen.
Ja, du kannst. Die CPython-VM ist sowohl für Windows als auch für Linux verfügbar, ebenso wie PyPy, Jython und IronPython.
Sprachen müssen nicht kompiliert oder interpretiert werden. Sprachen gerade sind . Tatsächlich kann eine Sprache perfekt existieren, ohne einen Interpreter oder Compiler zu haben! Zum Beispiel wurde Konrad Zuses Plankalkül, den er in den 1930er Jahren entwarf, zu seinen Lebzeiten nie umgesetzt. Sie könnten immer noch Programme darin schreiben, Sie könnten diese Programme analysieren, Gründe dafür angeben, Eigenschaften für sie beweisen ... Sie könnten sie einfach nicht ausführen. (Nun, eigentlich ist auch das falsch: Sie können sie natürlich in Ihrem Kopf oder mit Stift und Papier laufen lassen.)
Jetzt kann jede bestimmte Implementierung einer Sprache einen Compiler (oder sogar mehrere Compiler), einen Interpreter oder eine beliebige Kombination verwenden. Aber das ist ein Merkmal der Implementierung , nicht der Sprache. Jede Sprache kann mit einem Compiler implementiert werden, und jede Sprache kann mit einem Interpreter implementiert werden.
Beachten Sie jedoch, dass Sie ein Programm ohne Interpreter nicht ausführen können. Ein Compiler übersetzt einfach ein Programm von einer Sprache in eine andere. Aber das ist es. Jetzt haben Sie das gleiche Programm, nur in einer anderen Sprache. Der einzige Weg, um tatsächlich ein Ergebnis des Programms zu erhalten, besteht darin , es zu interpretieren . Manchmal ist die Sprache eine extrem einfache binäre Maschinensprache, und der Interpreter ist tatsächlich in Silikon fest codiert (und wir nennen es eine "CPU"), aber das ist immer noch Interpretation.
Diese Antwort könnte Sie auch interessieren, in der die Unterschiede und die verschiedenen Möglichkeiten zum Kombinieren von Interpreten, JIT-Compilern und AOT-Compilern sowie die Antwort auf die Unterschiede zwischen einem AOT-Compiler und einem JIT-Compiler erläutert werden .