Unsere Datenschutzrichtlinie wird in Kürze aktualisiert. Bitte sehen Sie sich die Vorschau an.

Java 7 Grundkurs

Konstruktoren werden nicht vererbt

Testen Sie unsere 2016 Kurse

10 Tage kostenlos!

Jetzt testen Alle Abonnements anzeigen
Bei der Vererbung werden Konstruktoren nicht vererbt – das hat auch seinen speziellen Grund. Alles dazu erfahren Sie in diesem Film an Beispielen.
09:27

Transkript

Wenn Sie Vererbungen einsetzen, dann erbt die Unterklasse alles von der Oberklasse, was dort nicht als "private" deklariert ist. Also insbesondere alle öffentlichen Methoden. Konstruktoren werden jedoch nicht vererbt. Und das hat auch seinen guten Grund. Nehmen wir einmal dieses Beispiel mit den zwei Klassen "Auto" und "Cabrio". Die Basisklasse, die Oberklasse, heißt "Auto", und sie deklariert einige Methoden. Die Unterklasse "Cabrio" erbt alle diese Methoden von "Auto" und deklariert diese weitere Methoden zum Öffnen und zum Schließen des Daches. Ein Konstruktor ist ja dazu da, ein Objekt zu konstruieren und zu initialisieren. Der Konstruktor der Klasse "Auto" kann also sehr gut Auto-Objekte erzeugen und initialisieren. Er hat allerdings keine Ahnung, wie er Cabrio-Objekte erzeugen soll. Er weiß nicht einmal, dass es überhaupt Cabrio-Objekte gibt. Denn die Vererbungsbeziehung ist ja allein in der Unterklasse beschrieben. Hier haben wir die Klasse "Auto", sie deklariert zwei private Attribute: Geschwindigkeit und Name. Dann gibt es hier drei verschiedene Konstruktoren, um Auto-Objekte mit verschiedenen Startwerten für diese beiden Attribute erzeugen zu können. Außerdem gibt es hier noch eine Handvoll Methoden, die die Funktionalität eines solchen Autos beschreiben. Die Cabrio-Klasse ist etwas kürzer. Sie erbt den größten Teil ihrer Funktionalität von "Auto". Das sehen wir hier. Class Cabrio extends Auto. Damit haben also auch Cabrios all diese Methoden, die wir gerade gesehen haben, und zusätzlich noch diese beiden Methoden zum Öffnen und zum Schließen des Daches. Das Cabrio merkt sich in dieser Variablen "Dach offen", in diesem Attribut, ob das Dach offen ist oder nicht. Da Konstruktoren nun nicht vererbt werden, gibt es also hier nicht diese drei verschiedenen Möglichkeiten, Cabrio-Objekte zu erzeugen, wie wir das gerade bei Auto gesehen haben. Hier, hier und hier. Stattdessen haben wir nur die Möglichkeit, die wir immer haben, wenn wir in einer Klasse gar keinen Konstruktor deklarieren, nämlich den vom Compiler geschenkten Standardkonstruktor zu benutzen. Wenn der Compiler feststellt, dass eine Klasse überhaupt keinen Konstruktor deklariert, dann generiert er einen Konstruktor ohne Parameter, der einfach eine Instanz dieser Klasse erzeugt und alle Attribute auf ihre Standardwerte setzt. Das heißt, wir können Cabrios erzeugen, indem wir diesen Standardkonstruktor aufrufen, so wie das hier in der Main Methode auch passiert. Die Klasse Auto deklariert einen Konstruktor, der den Namen des Autos übernimmt. Wenn wir das aber hier beim Cabrio auch versuchen, und z. B. diese Cabrio "Car" nennen möchten, dann bekommen wir einen Compiler-Fehler. Klar, diesen Konstruktor gibt es ja in der Klasse nicht. Damit es ihn gibt, müssen wir ihn hinein schreiben. Machen wir das mal. Auch hier können wir uns wieder mit Steuerung+Leertaste ein bisschenTipparbeit sparen. Wir bekommen hier nämlich die Konstruktoren schon vorgeschlagen. Nehmen wir den hier, "Cabrio Name". Das ist genau der, den wir haben wollen. "Enter". Schauen wir uns einmal an, was da jetzt generiert wurde. Der Konstruktor heißt so, wie die Klasse, das ist in Ordnung. Er gibt auch nichts zurück. Darf ein Konstruktor ja gar nicht. Er nimmt den Namen, in Form eines Strings, das ist auch okay. Aber die Zeile hier ist neu. Die sieht anders aus, als wir das in der Klasse Auto gesehen haben. Schau noch mal in Auto hinein. Hier ist der entsprechende Konstruktor. Der nimmt den Namen, und dieser Konstruktor reicht weiter per ds(0,NAME) an einen anderen Konstruktor der einen Int nimmt und einen String, das ist dieser hier. Der setzt die entsprechenden Attribute auf die zugehörigen Werte. Was wir im Cabrio jetzt also vielleicht erwartet hätten, wäre eine Zeile wie diese hier. Immerhin nimmt der Cabrio-Konstruktor ja den Namen entgegen und soll das Attibut Name auf diesen übergebenen Namen setzen. Diese Zeile kann aber in der Unterklasse gar nicht funktionieren. Das Attribut Name ist nämlich private und private bedeutet: Nur diese Klasse, in der es deklariert wird, darf darauf zugreifen. Und diese Klasse ist die Klasse Auto. Die Unterklasse Cabrio hat also keine Möglichkeit, an dieses Attribut direkt heranzukommen. Deshalb macht es sich der Konstruktor der Unterklasse recht bequem. Dieser Aufruf hier heißt nämlich nichts anderes als: Ruf' doch mal den Konstruktor der Oberklasse auf, der diesen Namen entgegennehmen kann. Wir nutzen hier also den Umstand, dass der Oberklassen-Konstruktor weiß, wie er eine Oberklassen-Instanz erzeugen und initialisieren soll. Die Klasse "Cabrio" erweitert ja die Klasse "Auto". Das heißt also, ein Cabrio besteht zum Teil aus dem, was in "Auto" deklariert wurde. Und diesen Teil initialisiert jetzt der Auto-Konstruktor. Unser Cabrio-Konstruktor muss nun lediglich den Teil des Cabrios initialisieren, der nicht bereits vom Auto-Konstruktor initialisiert wurde. Also sprich alles, was im Cabrio dazugekommen ist. In unserem Fall ist das dieses eine Attribut "Dach offen". Dieses Attribut wird jetzt von diesem Konstruktor mit seinem Standardwert initialisiert, das wäre in unserem Fall "false". Damit sind wir auch zufrieden, deswegen müssen wir in diesem Konstruktor nichts weiter hinein schreiben. Das führt uns natürlich zu dem Wunsch, ein Cabrio erzeugen zu können, das gleich, wenn es vom Fließband rollt, ein offenes Dach hat. Anders ausgedrückt, wir möchten gerne einen zweiten Konstruktor haben, der zwei Parameter nimmt. Kein Problem, bauen wir uns einen. Steuerung+Leertaste weist den Weg. Dieser hier sieht genau so aus, wie das, was ich meine. Ein Konstruktor der zwei Parameter nimmt. Nämlich einmal einen booleschen Wert für "Dach offen" und einen Namen. Wählen wir den also aus. "Enter". Wie wir sehen, ist der erste Teil dieses Konstruktors wieder derselbe wie eben schon. Es wird an den Konstruktor der Oberklasse delegiert. Wenn der dort oben fertig ist mit der Initialisierung des Autoteils unseres Cabrios, dann kehrt der Aufruf zurück, und wir können jetzt den Cabrio-Teil unseres Cabrios initialisieren, das heißt wir können jetzt sagen: "Mach doch mal das Dach gleich auf."  Eine Kleinigkeit wäre jetzt hier noch zu ändern. Schauen wir dazu nochmal kurz in die Klasse "Auto" hinein. Wir haben hier drei Konstruktoren. Einer nimmt zwei Parameter, einer nimmt einen Parameter und einer nimmt gar keinen. Der mit den meisten Parametern initialisiert die Attribute mit den übergebenen Werten. Die anderen beiden Konstruktoren reichen lediglich an diesen weiter und übergeben für die fehlenden Parameter Standardwerte. Der Konstruktor ohne Parameter legt fest, dass der Name "Anonym" heißen soll und gibt damit weiter an diesen. Dieser fügt die Geschwindigkeit "null" hinzu und übergibt damit an den Konstruktor, der einen Int und einen String nimmt, das ist also der. Und dieser eine führt also die eigentliche, vollständige Initialisierung des Objektes durch. Die anderen leiten lediglich weiter. Vorteil: Wir haben die Initialisierung des Objektes an einer Stelle in unserem Code einmal hingeschrieben und vermeiden dadurch unnötige Wiederholungen. Zugegeben, unsere Initialisierung ist hier etwas schmal, aber Sie können sich sicher vorstellen, dass hier noch ein bisschen mehr Tests und Abfragen stattfinden könnten. Dann wäre das eine Gute Idee, die tatsächlich nur hier an dieser einen Stelle stehen zu haben. Übertragen wir das nun auf unsere Unterklasse "Cabrio". Hier haben wir zwei Konstruktoren. Einer nimmt zwei Parameter und einer nimmt einen Parameter. Den ohne Parameter haben wir noch gar nicht dabei, können wir aber problemlos hinzufügen. Machen wir gleich noch. Wenn wir das genauso aufbauen, wie wir das in der Oberklasse gemacht haben, dann heißt das, dass der Konstruktor mit den meisten Parametern - das ist dieser hier - die Initialisierung vornimmt. Das heißt also, hochreichen, oben machen lassen, wieder hinunter kommen, Rest des Cabrios initialisieren, und die anderen Konstruktoren sollten lediglich an diesen weiterreichen. Statt "Super Name" schreiben wir hier also stattdessen hin: "This false, Name". Das heißt, wenn wir ein Cabrio erzeugen, wir geben einfach nur den Namen. Dann wird hier weitergeleitet an den anderen Konstruktor, der einen Boolean nimmt und einen String, das ist dieser hier. Und für Dach offen wird "false" als Standardwert übergeben. Damit können Sie sich nun vielleicht schon denken, wie der Standardkonstruktor aussieht. Ich tippe den mal so rein: "Cabrio()". Wir möchten hier weitergeben an den einen anderen Konstruktor, disen hier, und hier, einen Standardnamen übergeben. Zum Beispiel so etwas. Was fehlt noch? Das Semikolon. Damit kommen wir zurück zu unserem Anfangswunsch, dass wir ein Cabrio bauen können und ihm einen Namen geben. Sie sehen, der Compiler-Fehler ist verschwunden. Jetzt funktioniert es also. Es gibt jetzt einen Konstruktor, der einen String nimmt. Und wenn wir gleich die Anwendung ausführen, dann wird also ein solches Cabrio gebaut. Und wenn wir hier "Get Status" aufrufen, dann wird die geerbte Methode Get Staus ausgeführt, die uns den Namen und die aktuelle Geschwindigkeit ausgibt. Starten wir mal das Programm. Und dann sehen wir hier: Cabrio fährt gerade ein km/h. Wir haben also gesehen, Konstruktoren werden nicht vererbt, möchten sie in der Unterklasse welche haben, dann müssen Sie sie auch dort deklarieren.

Java 7 Grundkurs

Machen Sie sich mit den Grundlagen der Java-Programmierung vertraut und lernen Sie die Syntax der Sprache sowie das Konzept der objektorientierten Softwareentwicklung kennen.

8 Std. 32 min (66 Videos)
Derzeit sind keine Feedbacks vorhanden...
 

Dieser Online-Kurs ist als Download und als Streaming-Video verfügbar. Die gute Nachricht: Sie müssen sich nicht entscheiden - sobald Sie das Training erwerben, erhalten Sie Zugang zu beiden Optionen!

Der Download ermöglicht Ihnen die Offline-Nutzung des Trainings und bietet die Vorteile einer benutzerfreundlichen Abspielumgebung. Wenn Sie an verschiedenen Computern arbeiten, oder nicht den ganzen Kurs auf einmal herunterladen möchten, loggen Sie sich auf dieser Seite ein, um alle Videos des Trainings als Streaming-Video anzusehen.

Wir hoffen, dass Sie viel Freude und Erfolg mit diesem Video-Training haben werden. Falls Sie irgendwelche Fragen haben, zögern Sie nicht uns zu kontaktieren!