Re: [J2SE] 多型與轉型
※ 引述《forris (喬巴)》之銘言:
: class Father{
: String name = "Father";
: String getName(){
: return name;
: }
: String greeting(){
: return "class Father";
: }
: }
: class Son extends Father{
: String name = "Son";
: String greeting(){
: return "class Son";
: }
: void foo(){
: System.out.println((Son)this).greeting();
: System.out.prtinln((Father)this).greeting();
這兩行code是手打的? 錯誤不少orz
System.out.println(( (Son)this).greeting());
System.out.println( ((Father)this).greeting());
: }
: }
: 要問印出來的訊息
: ((Son)this).greeting() 是指 Son 類別的 greeting(), 所以訊息為 class Son.
: ((Father)this).greeting() 是指 Son 類別的 greeting(), 但是為 Father 型別,
: 出現的訊息不應該跟著轉型後的型別走嗎?
: 怎麼不是 class Father 而是 class Son ?
這是overridding(覆蓋)的問題
子類別繼承父類別的時候如果複寫掉父親的方法,
則由子類別產生的物件實體就只會具有子類別所時做的方法.
(如果需要使用父類別的方法,只能在子類別內透過super關鍵字呼叫。)
如果你單純記實體不實體的話,可能會翻船。
比方說下列的狀況
void foo(){
Father father = ((Father) this);
Son son = ((Son) this);
System.out.println(father.greeting());
System.out.println(son.greeting());
System.out.println(father.name);
System.out.println(son.name);
}
請問後面兩個name印出來的會是什麼? :)
這個就自己試試看吧
這跟method的差異是method是直接被覆蓋,
member的話,只是被子member給「遮掩」而已。
(有點類似local variable跟member variable需要透過this區隔的差異)
所以當我在son內如果有需要取得father的greeting()的時候
要盡量透過super.greeting() 來處理,而避免透過轉型。
同樣的要存取父類別name也是透過super.name來處理
System.out.println(super.name);
最後再說一個有趣的問題,如果原po所認為的跟著型態成立,
當Father是abstract Class, 沒有實做greeting(),
轉型回Father再呼叫greeting() , 這時候就會有問題了,
會連帶的影響abstract Class不能藉由轉型來操作。
所以還是隨時搞懂自己再用那個類別,類別有哪些屬性跟方法,
按照它提供給你的文件去處理,按照不同類別的功能去處理,
不要任意去猜測它應該提供給你什麼,這樣會比較好。
這樣也可以保持他的黑盒子特性~
--
I am a person, and I am always thinking .
Thinking in love , Thinking in life ,
Thinking in why , Thinking in worth.
I can't believe any of what ,
I am just thinking then thinking ,
but worst of all , most of mine is thinking not actioning...
--
※ 發信站: 批踢踢實業坊(ptt.cc)
◆ From: 59.117.162.40
討論串 (同標題文章)