Почему переменная" Class " не может быть передана в instanceof?
почему этот код не компилируется?
public boolean isOf(Class clazz, Object obj){
if(obj instanceof clazz){
return true;
}else{
return false;
}
}
почему я не могу передать переменную класса instanceof
?
4 ответа:
The
instanceof
оператор работает на ссылочных типах, таких какInteger
, а не на объекты, какnew Integer(213)
. Вы, наверное, хотите что-то вродеclazz.isInstance(obj)
Примечание: ваш код будет более кратким, если вы напишите
public boolean isOf(Class clazz, Object obj){ return clazz.isInstance(obj) }
не совсем уверен ,что вам нужен метод больше, хотя.
instanceof
может использоваться только с явными именами классов (указанными во время компиляции). Для того, чтобы сделать runtime проверить, вы должны сделать:clazz.isInstance(obj)
это имеет небольшое преимущество над
clazz.isAssignableFrom(..)
так как он имеет дело с деломobj == null
лучше.
во-первых,
instanceof
требует, чтобы операнд справа был фактическим классом (например,obj instanceof Object
илиobj instanceof Integer
), а не переменная типаClass
. Во-вторых, вы сделали довольно распространенную ошибку новичка, которую вы действительно не должны делать... следующая картина:if ( conditional_expression ){ return true; } else{ return false; }вышесказанное может быть преобразовано в:
return conditional_expression;вы всегда должны выполнять этот рефакторинг, так как он устраняет избыточный if...еще заявление. Аналогично, выражение
return conditional_expression ? true : false;
это refactorable в тот же результат.
как уже упоминалось, вы не можете передать переменную класса в
instanceof
потому что переменная класса ссылается на экземпляр объект, в то время как правая рукаinstanceof
должен быть тип. То есть,instanceof
не означает "y является экземпляром объекта x", это означает"y является экземпляром типа X". Если вы не знаете разницы между объектом и типом, подумайте:
Object o = new Object();
вот, типа
Object
, иo
является ссылкой на экземпляр объекта с этим типом. Таким образом:
if(o instanceof Object)
допустима, но
if(o instanceof o)
не так
o
С правой стороны-это объект, а не тип.более конкретно для вашего случая, экземпляр класса не является типом, это объект (который создается для вас JVM). В вашем методе,
Class
- это тип, ноclazz
- это объект (ну, ссылка на Объект)вам нужен способ сравнить объект с объектом класса. Оказывается, что это популярно, поэтому это предоставляется вам как метод объекта класса:
isInstance()
.вот Java Doc для isInstance, который объясняет это лучше:
public boolean isInstance(Object obj)
определяет, совместим ли указанный объект с назначением объект, представленный этим классом. Этот метод является динамическим эквивалент оператор instanceof языка Java. Метод возвращает true, если указанный аргумент объекта не равен null и может быть приведение к ссылочному типу, представленному этим объектом класса без создание ClassCastException. В противном случае он возвращает false.
в частности, если этот объект класса представляет объявленный класс, это метод возвращает true, если указанный аргумент объект является экземпляром представленный класс (или любого из его подклассов); он возвращает false иначе. Если этот объект класса представляет класс массива, этот метод возвращает true если указанное Object параметр может быть преобразован в объект класса массива путем преобразования идентификатора или путем расширения преобразование ссылок; в противном случае он возвращает false. Если этот объект класса представляет интерфейс, этот метод возвращает true, если класс или любой суперкласс указанного аргумента объекта реализует этот интерфейс; в противном случае он возвращает false. Если этот объект класса представляет собой тип примитива, этот метод возвращает false.
параметры: obj - объект для проверки
возвращает: true, если obj является экземпляром этого класса
С тех пор: JDK1.1