Warum trägt eine Java-Quelldatei den Namen der darin enthaltenen öffentlichen Klasse?

14

Ich bin ein Neuling, der Java lernt. In Java muss jede Quelldatei eine öffentliche Klasse enthalten, und diese Quelldatei muss denselben Namen wie diese öffentliche Klasse haben. Darüber hinaus kann keine Quelldatei zwei öffentliche Klassen enthalten. Warum ist diese Einschränkung?

Benutzer
quelle
4
Ohne die Details ist dies ein historisches Design-Artefakt der Art und Weise, wie Java entwickelt wurde. In neueren Sprachen wie C # gilt diese Einschränkung nicht, obwohl sie Java ähnelt.
Gahooa
13
Ist es nicht Best Practices durchzusetzen? Ich dachte das wäre der einzige Grund. In C # gibt es diese Einschränkung auf technischer Ebene nicht. StyleCop beklagt sich jedoch, wenn Dateiname und Klassenname nicht übereinstimmen oder wenn Sie mehrere Klassen in derselben Datei haben. Visual Studio unterstützt auch die Klassen-Dateibeziehung in hohem Maße (denken Sie an Klassendiagramme, die Dateien für Sie erstellen, oder wenn Sie die CS-Datei umbenennen, werden Sie von Visual Studio gefragt, ob Sie den Namen der Klasse ebenfalls umgestalten möchten).
Arseni Mourzenko 16.01.12
In einer kompilierten Sprache alten Stils findet der Linker alle Referenzen und externen Symbole. Java ist jedoch nicht verknüpft - Sie können JARS zur Laufzeit laden, wenn Sie möchten. Ohne einen Verknüpfungsschritt ist der Versuch, Klassennamen Positionen im Klassenpfad zuzuordnen, viel schneller, wenn Sie wissen, nach welchem ​​Dateinamen Sie suchen müssen.
Paul Tomblin
4
@gahooa es ist kein Design-Artefakt, es ist eine bewusste Design-Entscheidung. Das macht vieles viel einfacher.
1
Was ist mit grep ?
Benutzer

Antworten:

19

Heinz Kabutz blättert in einem seiner Java Specialists 'Newsletter in den Oak Language Specifications . Er schreibt:

Warum befindet sich jede öffentliche Klasse in einer eigenen Datei? (Abschnitt 1)

Dies ist eine Frage, die mir während meiner Kurse häufig gestellt wurde. Bis jetzt hatte ich keine gute Antwort auf diese Frage. In Abschnitt 1 lesen wir: "Obwohl jede Oak-Kompilierungseinheit mehrere Klassen oder Schnittstellen enthalten kann, kann höchstens eine Klasse oder Schnittstelle pro Kompilierungseinheit öffentlich sein."

In der Seitenleiste wird erklärt, warum: "Diese Einschränkung wird vom Compiler noch nicht erzwungen, obwohl sie für einen effizienten Paketimport erforderlich ist."

Es ist ziemlich offensichtlich - wie die meisten Dinge sind, wenn Sie die Designgründe kennen -, dass der Compiler zusätzlich alle Kompilierungseinheiten (.java-Dateien) durchlaufen muss, um herauszufinden, welche Klassen wo sind, und dies würde die Kompilierung noch langsamer machen .

http://www.javaspecialists.eu/archive/Issue055.html

Landei
quelle
1
Um die Erstellung geringfügig schneller? "Ja wirklich?" Nicht weil es Ihren Code viel besser organisiert? Ich bezweifle sehr, dass dies die richtige Antwort ist.
BlueRaja - Danny Pflughoeft
1
@ BlueRaja-DannyPflughoeft Im Jahr 1998, ich bin sicher, es machte einen viel größeren Unterschied
TheLQ
8

Gründe, die mir einfallen

  • Erleichtert dem Compiler das Finden anderer Klassen am Anfang etwas, da er nicht alle potenziell Tausenden von Klassendateien nach einer zufälligen öffentlichen Klasse durchsuchen muss, sondern einfach in die Datei wechseln kann.
    • Das spielt wahrscheinlich keine Rolle mehr, sondern hat gerade die frühe Convention begonnen, die sich nie geändert hat
  • Beim Kompilieren wirkt sich eine Änderung an einer Datei nur auf diese Datei aus. Wenn es mehrere Klassen gibt, muss alles neu kompiliert werden
  • Bewährtes Verfahren - Wenn mehrere öffentliche Klassen in derselben Datei enthalten sind, ist dies verwirrend. Der Zweck von Dateien ist es, den Quellcode zu organisieren, der Zweck von Ordnern ist es, die Dateien zu organisieren. Wenn sich alle Klassen eines bestimmten Pakets in einer einzigen 100-MB-Super-Datei befinden, haben Sie alle Vorteile verloren und keinen der Vorteile von Dateien gewonnen (und beim Bearbeiten viel Kopfzerbrechen verursacht).
TheLQ
quelle
1
Klassen und Interfaces stellen nicht notwendigerweise die natürlichste Ebene von Unterteilungen für Quellcode dar. Es ist unpraktisch, viele tausend Codezeilen in einer Datei zu haben, aber es ist auch unpraktisch, 100 Zeilen "echten" Inhalts (ohne Kommentare oder duplizierte Compiler-Direktiven) in einem Dutzend Quelldateien zu haben. Ich frage mich, wie es funktionieren würde, wenn eine Datei mit dem Namen des Typs entweder die Definition enthalten oder die Datei identifizieren müsste , die dies tut.
Supercat