簡體   English   中英

執行Casting時發生執行階段例外

[英]Runtime exception when doing a Casting

進行Casting時出現運行時異常,如下所示

線程“主”中的異常java.lang.ClassCastException:無法在Testing.main(Testing.java:5)上將A強制轉換為B

public class A {

    public void printA()
    {
        System.out.println("A");
    }

}




public class B extends A{

    public void printB()
    {
        System.out.println("B");
    }
}

public class Testing {

    public static void main(String args[]) {

        B b = (B) new A();
        b.printA();
    }

}

但是為什么這段代碼可以正常運行

因為我們在這里做同樣的事情

HttpServletRequest request = (HttpServletRequest) req;

public class LogFilter implements Filter {
    public void doFilter(ServletRequest req, ServletResponse res,FilterChain chain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) req;
        String ipAddress = request.getRemoteAddr();
        chain.doFilter(req, res);
    }

由於req具有HttpServletRequest實際類型,因此可以向下轉換。

您可以使用System.out.println(req.getClass());

但是,在你的情況你的實際對象類型的A ,因為new A()所以你不能將其轉換B

可行的方案:

A a = new B(); //actual type is B
B b = (B)a;

第二條陳述B b = (B)a; 被允許,因為它被創建時的對象的實際類型是B由於new B()只是引用類型是A 因此,您可以再次將其轉換回B

您不是在做同一件事。

在第二個示例中,req是HttpServletRequest的實例。

在第一個示例中,A不是B的實例。

A不是B的實例,因此您不能在這種情況下灰心。

考慮一下,A是動物,B是布法羅。

現在,布法羅擴展了Animal。

然后,在您的代碼中執行以下操作:

Buffalo b =(Buffalo)new Animal();

這是錯誤的,因為動物沒有擴大水牛城!

您應該僅將對象強制轉換為一個類。

因此,如果您有擴展“動物”的水牛城,則可以將其投射為“動物”(因為它是其中一個)。

但是您不能將動物投擲到水牛城,因為並非所有動物都是水牛城。

您是在告訴編譯器(通過顯式強制轉換)信任您您沒有犯錯誤,因此它忽略了錯誤並且在編譯時未檢測到錯誤。 這就是為什么您不會遇到編譯錯誤的原因 但是,當程序運行時,您會得到一個異常,因為A 不是 B的實例。 您可能想做:

A b = (A) new B();

請注意,如果刪除顯式強制轉換,則會出現編譯錯誤 (總是首選),因為編譯器已經知道您在做錯誤。

在另一個示例中,您認為它是相同的..嗯..這是不相同的,那里, reqHttpServletRequest一個實例。

當你做一個new A ,你不能將它轉換為B ,因為B是的子類A (又該否則屬性和mothods定義B ,但不是A樣子?)

HttpServletRequest request = (HttpServletRequest) req; req是在其他地方創建的,它是一個HttpServletRequest

原因HttpServletRequestServletRequest 在您的示例中, A不一定是B ,可以是AC或任何子類。

讓我們來看看動物的例子,它更容易。

class Animal{}
class Dog extend Animal{}
class Cat extend Animal{}

在主要。

       Animal a= new Animal();
       Dog dog = (Dog)a;// A dog is an animal but not all animals are  dog

動物不可能是狗,也可能是貓,或者像本例中的Animal這樣的其他東西,然后ClassCastException 為了避免此runtimeException,可以使用instanceof運算符。

這不會引發異常,因為servletrequest是HttpServletRequest的超級接口。

這類似於動態多態性。 如果您編寫了一個接口B,然后將A對象轉換為B,那么它將起作用。

http://docs.oracle.com/javaee/6/api/javax/servlet/http/HttpServletRequest.html

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM