Пример «instanceof»

public class TableModel2 extends TableModel1 { ... }

TableModel2 tableModel = new TableModel2();

boolean t1 = tableModel instanceof TableModel1;
boolean t2 = tableModel instanceof TableModel2;

В приведенном выше примере t1 и t2 равны true. Итак, как я могу отличить TableModel1 от TableModel2, используя instanceof?


person Klausos Klausos    schedule 07.02.2012    source источник


Ответы (7)


Вы не можете сделать это с помощью instanceof, но вы можете сделать это с помощью getClass:

boolean t1 = tableModel.getClass().equals(TableModel1.class);
boolean t2 = tableModel.getClass().equals(TableModel2.class);

Оператор instanceof предназначен для проверки всей иерархии классов, вплоть до java.lang.Object, включая проверки для всех интерфейсов. Он позволяет узнать, можно ли привести экземпляр объекта, который у вас есть, к указанному вами типу, не вызывая исключения приведения класса.

getClass, с другой стороны, возвращает конкретный класс данного объекта.

person Sergey Kalinichenko    schedule 07.02.2012

Итак, как я могу отличить TableModel1 от TableModel2, используя instanceof?

Технически вы можете проверить, что tableModel является экземпляром TableModel1, а не экземпляром TableModel2:

(tableModel instanceof TableModel1) && !(tableModel instanceof TableModel2)

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

person NPE    schedule 07.02.2012
comment
Что произойдет, если я добавлю TableModel3? TableModel25? - person alf; 07.02.2012

экземпляр означает "является".

TableModel2 IS A TableModel1.
But TableModel1 IS NOT A TableModel2.
so

package main;

public class TempClass {
    public static void main(String[] args) {
        TableModel1 tableModel1 = new TableModel1();
        TableModel1 tableModel2 = new TableModel2();

        System.out.println(tableModel1 instanceof TableModel1);
        System.out.println(tableModel1 instanceof TableModel2);

        System.out.println(tableModel2 instanceof TableModel1);
        System.out.println(tableModel2 instanceof TableModel2);
    }

    public static class TableModel1 {
    }

    public static class TableModel2 extends TableModel1 {
    }
}

true
false

true
true
person kornero    schedule 07.02.2012
comment
открытый класс TableModel2 extends TableModel1 { ... } Поэтому instanceOf здесь не работает - person Klausos Klausos; 07.02.2012
comment
tableModel1 и tableModel2, они оба являются TableModel1. Таким образом, пример дает истину. Но tableModel1 НЕ ЯВЛЯЕТСЯ TableModel2. - person kornero; 07.02.2012

Вы не можете. Если вам действительно нужно отличить одно от другого, используйте вместо этого tableModel.getClass(), например:

boolean t1 = tableModel.getClass() == TableModel1.class;
boolean t2 = tableModel.getClass() == TableModel2.class;

Обратите внимание, что вы намеренно пытаетесь нарушить один из основополагающих принципов ООП, поэтому убедитесь, что вы не можете избежать этого трюка, прежде чем использовать его в реальном коде.

person alf    schedule 07.02.2012

Ну, я не верю, что ты можешь. С точки зрения наследования tableModel является абсолютно допустимой ссылкой для обоих типов, поэтому instanceof вернет true в обоих случаях.

person ŁukaszBachman    schedule 07.02.2012

Легко, используйте имена классов:

public class Test
{
    public class TableModel1
    {
    };

    public class TableModel2 extends TableModel1
    {
    };

    public TableModel2 tableModel = new TableModel2();

    public static void main(String[] args)
    {
        Test t = new Test();
        System.out.println("t1=" + t.tableModel.getClass().equals(TableModel1.class));
        System.out.println("t2=" + t.tableModel.getClass().equals(TableModel2.class));
    }
}
person Fernando Miguélez    schedule 07.02.2012

person    schedule
comment
Перед этим добавляется проверка NULL для tableModel, тогда как instanceof этого не требует. - person Kanagavelu Sugumar; 28.01.2016