JAVA向上轉型和向下轉型(二)

xiaolong_hui發表於2017-03-10
             
  JAVA向下轉型是不安全的。為什麼呢?舉個例子。
  定義父類:
 public class Animal {
    public void eat(){
        System.out.println("吃飽了!");
    }
 }
   
子類:
public class Dog extends Animal {
    public void run(){
        System.out.println("跑起來!!");
    }
}

public class Bird extends Animal {
    public void fly(){
        System.out.println("飛起來!!");
    }
}

編寫以下程式碼,執行:
        Animal a = new Animal();
        Bird b = (Bird)a;//向下轉型
        b.eat();
        b.fly();
編譯沒有問題,執行報錯:Exception in thread "main" java.lang.ClassCastException: cn.xl.c3.Animal cannot be cast to cn.xl.c3.Bird
    at cn.xl.c3.Test.main(Test.java:14)

結論:
  1. 向上轉型時,父類指向子類引用物件會遺失子類獨有的新函式,在編譯時,系統會提供找不到方法的錯誤。

  2. 向上轉型是安全的。

  3. 向下轉型的過程中是不安全的,編譯不會出錯,但是執行時會出現java.lang.ClassCastException錯誤。它可以instanceof來避免出錯此類錯誤。


JAVA虛擬機器呼叫一個類方法時,它會基於物件引用的型別(通常在編譯時可知)來選擇所呼叫的方法。相反,當虛擬機器呼叫一個例項方法時,它會基於物件實際的型別(只能在執行時得知)來選擇所呼叫的方法,這就是動態繫結,是多型的一種。動態繫結為解決實際的業務問題提供了很大的靈活性,是一種非常優美的機制。——《JAVA動態繫結的內部實現機制》,作者 飛天金剛 。

由此可見,向下轉型時,編譯通過,但是執行的過程中虛擬機器需要呼叫引用指向的例項方法,這時就會出現問題。

向上轉型既然不安全是不是就沒有用了,答案是否定的。詳情參加《JAVA向上轉型和向下轉型(三)》

相關文章