只是因爲protected
或public
non-final方法是由子類覆蓋,這是腳步到初始化問題。假設重寫方法試圖在初始化之前訪問一個字段,你會得到一個NullPointerException
。假設它調用另一種方法,它依賴於在完全初始化之前不能保證的特定對象狀態,這會導致程序更加微妙的錯誤或不正確。
我要說的是已經在你的書了,所以讓我們添加一個具體的例子:
public SpaceShip {
private double oilLevelInLitres;
private String model;
public SpaceShip(double oilLevelInLitres, String model) {
this.oilLevelInLitres = oilLevelInLitres;
displayOilLevel();
this.model = model;
}
public void displayOilLevel() {
System.out.println("Oil level is currently " + oilLevelInLitres + " litres");
}
}
public SpaceShipWithSecondaryReservoir {
public SpaceShip(double oilLevelInLitres, double secondaryReservoirOilLevelInLitres, String oilLevelInLitres) {
super(oilLevelInLitres, oilLevelInLitres);
this.secondaryReservoirOilLevelInLitres = secondaryReservoirOilLevelInLitres;
}
public void displayOilLevel() {
System.out.println("Model " + model + " oil level is currently " + oilLevelInLitres +
" litres and " + secondaryReservoirOilLevelInLitres + " litres in the seconday reservoir");
}
}
public Main() {
public static void main(String[] args) {
// will print "Model null oil level is currently 17.0 litres and 5.0 litres in
// the secondary reservoir"
new SpaceShipWithSecondaryReservoir(17, 5, "Falcon-3X");
}
}
在這個例子中,你可能會說,父類也可以初始化model
名調用方法前,而且你是對的,但是現在程序員編寫了父類構造函數,他假定顯示方法不需要除油位以外的任何其他狀態。
這是一個編程錯誤,通過在構造函數的末尾調用display方法可以避免,但在更復雜的情況下,它不會那麼簡單和明顯。在構造函數中調用可重寫的方法會讓您遇到一類在您只調用final或private方法時不存在的錯誤。
我已經添加了一個例子來說明 – Dici