簡體   English   中英

Java:instanceof 也可以檢查“封閉類”嗎?

[英]Java: Can instanceof also check "enclosing classes"?

instanceof 是否也能夠檢查封閉的 class (不確定這是否是我的問題的正確措辭)?

請看下文。

汽車.java

public class Car
{
    public static class Wheel {}
}

class CarA extends Car {}

class CarB extends Car {}

x.java

public class x
{
    public static void main (String [] args)
    {
        System.out.println ("*******");
        
        CarA.Wheel caw = new CarA.Wheel ();
        CarB.Wheel cbw = new CarB.Wheel ();
        System.out.println (caw instanceof CarA.Wheel);
        System.out.println (caw instanceof CarB.Wheel);
        System.out.println (cbw instanceof CarA.Wheel);
        System.out.println (cbw instanceof CarB.Wheel);
    }
}

** Output 是 **

true
true
true
true

但我正在尋找

true
false
false 
true

我知道 Wheel 由於擴展而總是相同的,但是有沒有辦法可以將 CarA/CarB 包含在檢查中(無需在 CarA 和 CarB 中實現 Wheel)?

您只有一個Wheel class。 Car.WheelCarA.WheelCarB.Wheel只是同一個 class 的不同名稱,這就是為什么instanceof對所有這些類型的計算結果都為 true 的原因。

在不(明確)在Wheel中引入新字段或讓每輛車都有自己的Wheel Car的情況下,另一種方法是使Wheel非靜態。 現在輪子知道它來自哪輛車。

public class Car
{
    public class Wheel {
        public Car getCar() {
            return Car.this;
        }
    }
}
Car.Wheel wheel = new CarA().new Wheel();
System.out.println(wheel.getCar() instanceof CarA); // true
System.out.println(wheel.getCar() instanceof CarB); // false

然而,在引擎蓋下,通過使其非靜態,一個合成字段被隱式添加到Wheel以記錄它來自哪輛車,所以你可能會認為這是“作弊”。

不,使用instanceof是不可能的。 正如您所提到的, Wheel class 僅存在一次。 僅僅因為您通過不同的路徑訪問它並不會使它成為不同的 class。

從功能上講,我不確定您是否需要為每種類型的汽車配備不同的車輪,或者您需要知道特定車輪屬於哪種類型的汽車。

在第一種情況下,答案很快:您需要將 class 復制到WheelAWheelB中。

在第二種情況下,您根本不應該使用instanceof來檢查。 你可以這樣做:

public class Car
{
    public static class Wheel<T extends Car> {

        private final Class<T> carType;

        public Wheel(Class<T> carType) {
            this.carType = carType;
        }

        public Class<T> getCarType() {
            return carType;
        }
    }
}

因此,您的代碼將更改如下:

public class x
{
    public static void main (String [] args)
    {
        System.out.println ("*******");
        
        CarA.Wheel<CarA> caw = new CarA.Wheel<> (CarA.class);
        System.out.println (caw.getCarType().equals(CarA.class));
        System.out.println (caw.getCarType().equals(CarB.class));
    }
}

這正是我發現內部類不清楚的原因(抱歉意見)

“靜態內部類”(它被稱為)只是在另一個 class 中聲明的一種 class,但它的反應方式與在 class 之外聲明的方式相同

And since it's static, it work exactly as if you had String constant: they have the same value in the parent and in the child classes: Car.Wheel.class == CarA.Wheel.class == CarB.Wheel.class

    System.out.println(CarA.Wheel.class == Car.Wheel.class);
    
    System.out.println(CarA.Wheel.class);
    System.out.println(CarB.Wheel.class);

印刷

true
class local.Car$Wheel
class local.Car$Wheel

而且由於您不能在 java 中覆蓋 static 的任何內容,因此沒有理由參考 CarA.Wheel 和 CarB.Wheel

對我來說,這是一個特定的意見,在這種情況下,你真的不需要做內部 class:汽車和車輪在 package 中可能處於同一水平。

不是 static 的內部類是另一回事。

暫無
暫無

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

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