java中用于比较不同类的instanceof运算符
我试图了解Java中instanceof操作符是如何工作的,我面临一个非常奇怪的问题java中用于比较不同类的instanceof运算符,java,instanceof,Java,Instanceof,我试图了解Java中instanceof操作符是如何工作的,我面临一个非常奇怪的问题 public static void main(String[] args) { Map m = new HashMap(); System.out.println("m instanceof Date: " + (m instanceof Date)); } 如上所示,返回false。但是, public static void main(String[] args) { HashM
public static void main(String[] args) {
Map m = new HashMap();
System.out.println("m instanceof Date: " + (m instanceof Date));
}
如上所示,返回false。但是,
public static void main(String[] args) {
HashMap m = new HashMap();
System.out.println("m instanceof Date: " + (m instanceof Date));
}
这甚至不编译。我犯了一个错误
inconvertible types
found : java.util.HashMap
required : java.util.Date
我错过了什么?
我使用的是IntelliJ Idea 11。来自Java语言规范3.0第15.20.2节: 如果将RelationalExpression强制转换为ReferenceType 作为编译时错误被拒绝,然后 表达式同样会产生编译时错误。以这样的方式 在这种情况下,instanceof表达式的结果永远无法 对
由于您无法编译从
HashMap
到Date
的强制转换,您也不能在两者之间编译instanceof
测试。您声明映射m
并使用instanceof
,因为映射
是一个接口
,它是一个新类,可以扩展日期实现映射
。其他(非日期)抽象类或类导致编译错误
public static void main(String[] args) {
Map m = new HashMap();
System.out.println("m instanceof Date: " + (m instanceof Date));
}
请参考此处提到的JLS规范
这在这里得到了很好的回答@在我看来,Bon Espresso几乎说了正确的答案。下面是我的小补充: 您必须了解instanceof的真正功能,因此定义: instanceof是一个二进制运算符,用于检查实例是否属于某种类型 因此,当您这样做时:
Map m = new HashMap();
在编译时,m实际上是一个接口,但对instanceof的实际测试发生在运行时,实例不是接口,因此编译器无法确定m后面的实例(实现此接口的某个类)是否真的是一个可以扩展日期的类
我的意思是你可以有一个这样声明的类:
class MyClass extends Date implements Map{
.....
}
然后你可以这样做:
Map myMap = new MyClass();
(myMap instanceof Date)
这将是完全合法的,因为MyClass实际上延长了日期
正如您所看到的,这里的想法是,如果instanceof检查成功的可能性最小,编译器不会抱怨
另一方面,在第二个示例中:
HashMap m = new HashMap();
您正在声明映射接口的实际实现,或实例。在这种情况下,编译器确信HashMap不会延长日期,因此会给您带来错误。完全同意……当我在编译器中尝试相同的方法时,发现了这一点……必须说您已经非常优雅地将其放置了:)