Как узнать подкласс из экземпляра базового класса?

Есть ли способ узнать имя производного класса из экземпляра базового класса?

например:.

class A{
    ....
}
class B extends A{
    ...
}
class c extends A{
    ...
}

теперь, если метод возвращает объект A, могу ли я узнать, имеет ли он тип B или C?

Ответ 1

используя либо instanceof, либо Class#getClass()

A returned = getA();

if (returned instanceof B) { .. }
else if (returned instanceof C) { .. }

getClass() будет возвращать либо из: A.class, B.class, C.class

Внутри if-предложения, которое вам нужно будет отключить - i.e.

((B) returned).doSomethingSpecificToB();

Тем не менее, иногда считается, что использование instanceof или getClass() является плохой практикой. Вы должны использовать polymorphism, чтобы избежать необходимости проверять конкретный подкласс, но я не могу больше рассказать вам об этой информации.

Ответ 2

Пробовали ли вы использовать instanceof

например.

Class A aDerived= something.getSomethingDerivedFromClassA();

if (aDerived instanceof B) {

} else if (aDerived instanceof C) {

}

//Use type-casting where necessary in the if-then statement.

Ответ 3

Короткий ответ на ваш вопрос

Есть ли способ узнать имя производного класса из объекта базового класса?

no, суперкласс не может указывать имя/тип подкласса.

Вам необходимо допросить объект (который является экземпляром подкласса) и спросить, является ли он: instanceof конкретным подклассом или называет его getClass().

Ответ 4

Есть два способа, которыми я могу думать 1) Один с использованием API отражения Java 2) Другой был бы с экземпляромOf

Другим методом может быть сравнение объектов с объектами, я не знаю, как это могло бы быть, вы можете попробовать это

Ответ 5

Вы можете сделать это в конструкторе подкласса

class A {
    protected String classname;
    public A() { this.classname = "A"; }
    public String getClassname() { return this.classname; }
}
class B extends A {
    public B() {
        super();
        this.classname = "B";
    }
}

So

A a = new A();
a.getClassname(); // returns "A"
B b = new B();
b.getClassname(); // returns "B"
((A)b).getClassname(); // Also returns "B"

Поскольку он заносится в объект "A", он вызывает функцию "A" getClassname(), но возвращает значение, заданное конструктором, который был конструктором "B".

Примечание. Вызовите super(); перед установкой