關於抽象類無法實例化,但是可以使用"new"來實例的疑問.
背景:昨天下午回答一個實習生問的問題,大致的經過是這樣的:
他問的:“爲什麼抽象類無法實例化,但是可以new出來一個實例,官方這麼說是什麼意思?而且去了各類論壇,回答的都是比較含糊其辭,切不到重點.說什麼是面向對象設計的規範balabala…”.
我心理想,這貌似是一個老生常談的問題…
我回答說:“我給你一個demo,帶你debug一下,流程走完了,剩下的你就自己體會下”
標題定義一個抽象類Animal:
package com.example.abstractl;
public abstract class Animal {
public abstract void eat(Food food);
}
定義Animal的兩個子類:
TomCat:
package com.example.abstractl;
public class TomCat extends Animal {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println("TomCat Eating -> " + food.getName());
}
}
JerryMicky:
package com.example.abstractl;
public class JerryMicky extends Animal {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println("JerryMicky Eating -> " + food.getName());
}
}
Food:
package com.example.abstractl;
public class Food {
private String name;
public Food(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
MainApp類:
package com.example.abstractl;
public class MainApp {
public static void main(String[] args) {
Animal animal1 = new Animal() {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println(food.getName());
}
};
animal1.eat(new Food("老八祕製腸粉"));
Animal animal2 = new Animal() {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println(food.getName());
}
};
animal2.eat(new Food("老八祕製辣椒醬"));
Animal animal3 = new Animal() {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println(food.getName());
}
};
animal3.eat(new Food("老八祕製灌湯包"));
Animal animal4 = new Animal() {
@Override
public void eat(Food food) {
// TODO Auto-generated method stub
System.out.println(food.getName());
}
};
animal4.eat(new Food("老八祕製滷煮"));
Animal tomcat = new TomCat();
tomcat.eat(new Food("三文魚"));
Animal jerryMicky = new JerryMicky();
jerryMicky.eat(new Food("奶酪"));
}
}
打個斷點,運行debug
現在只要關注Debug棧幀窗口(綠色框),觀察**局部變量表(Variables)**裏的數據:Name列與Value列
此時注意看到debug棧幀窗口的Value列,有個"MainApp$1" ~ "MainApp4"對象.
“右鍵"其中的某一行,比如:“animal3”—選擇"Open Declared Type Hierarchy”.
看到如下圖的Type Hierarchy窗口(紅色框):
“$” 這就表示個內部類.而且還是個匿名內部類,而且還是作爲局部變量的匿名內部類.
寫道最後:
其實這個demo,也許寫的不嚴謹.但是也基本說明:
爲什麼"抽象類只能被子類化。它不能被實例化。抽象類可以包含抽象方法,即已聲明但未實現的方法。然後,子類提供抽象方法的實現。"的官方說明
好像從直觀上說:
“可以通過關鍵字來new一個抽象類來生成一個實例,但其實不是的,生成的僅僅是它的子類的對象.”
(好久不用md格式編輯,有點忘了,排版見諒).
OK,解釋到此結束.