Initialisieren final Felder in Java
Habe ich eine Klasse mit vielen final-Mitglieder, die instanziiert werden können mit einem der beiden Konstruktoren. Die Konstruktoren haben einige code, der gespeichert ist in einer Dritten Konstruktor.
//SubTypeOne and SubTypeTwo both extend SuperType
public class MyClass {
private final SomeType one;
private final SuperType two;
private MyClass(SomeType commonArg) {
one = commonArg;
}
public MyClass(SomeType commonArg, int intIn) {
this(commonArg);
two = new SubTypeOne(intIn);
}
public MyClass(SomeType commonArg, String stringIn) {
this(commonArg);
two = new SubTypeTwo(stringIn);
}
Das problem ist, dass dieser code nicht kompilieren: Variable 'two' might not have been initialized.
Jemand könnte möglicherweise rufen Sie den ersten Konstruktor von innen MyClass, und dann das neue Objekt hätte keine "zwei" - Feld gesetzt.
Also, was ist die bevorzugte Methode zum teilen von code zwischen Konstruktoren in diesem Fall? Normalerweise würde ich eine helper-Methode, aber der freigegebene code muss in der Lage sein, die endgültige Variablen, die nur aus einem Konstruktor.
In den ersten Konstruktor, zwei ist nicht initialisiert.
Skeet - Look wieder, die Parametertypen unterschiedlich sind.
Danke, ja, ich verpasst hatte. Doh.
InformationsquelleAutor Brian Gordon | 2013-02-15
Du musst angemeldet sein, um einen Kommentar abzugeben.
Wie über dieses? (Aktualisiert, geändert Frage)
Verständlich. Wie wäre es damit? Es vermeidet, dass Sie keine Unterklasse von
SuperType
, vermeidet Doppelarbeit und weist immer auf beide Variablen. Beachten Sie, Form auf dernull
um Unklarheiten zu vermeiden. gist.github.com/stickyd/4965120InformationsquelleAutor
Müssen Sie sicherstellen, dass in jedem Konstruktor Sie die Initialisierung aller final Variablen. Was ich tun würde, haben einen Konstruktor, initialisiert alle Variablen und alle anderen Konstruktor aufrufen, und übergeben Sie in
null
oder einige default-Wert, falls dort ein Feld ist, dass Sie nicht ein Wert für sich.Beispiel:
InformationsquelleAutor
Alles, was Sie tun müssen, ist sicherzustellen, dass "zwei" wird initialisiert. In den ersten Konstruktor, nur hinzufügen:
sei denn, es gibt einige andere Wert, den Sie möchten, geben es den Fall, dass nur der erste Konstruktor aufgerufen wird.
two
ist endgültig.Sie initialisieren eine final-variable zu null. Es muss nur initialisiert werden etwas. Wenn Sie wollen, zwei haben einen nicht-null-Wert, dann musst du zum aufrufen einer der anderen Konstrukteure. Es hat die gleiche Ergebnis als Sticky ' s Antwort.
Aber der Punkt ist, dass wenn ich
two
auf null in den ersten Konstruktor, dann kann ich nicht den tatsächlichen Wert in den anderen Konstruktoren, weil es bereits gesetzt wurde.InformationsquelleAutor
Erhalten Sie diesen Fehler, weil, wenn Sie genannt hatte
MyClass(SomeType oneIn)
,two
ist nicht initialisiert.InformationsquelleAutor