instanceof vs getClass()
使用getClass()
和==
运算符优于instanceOf
运算符时,我看到了性能的提高。
Object str = new Integer("2000"); long starttime = System.nanoTime(); if(str instanceof String) { System.out.println("its string"); } else { if (str instanceof Integer) { System.out.println("its integer"); } } System.out.println((System.nanoTime()-starttime)); starttime = System.nanoTime(); if(str.getClass() == String.class) { System.out.println("its string in equals"); } else { if(str.getClass() == Integer.class) { System.out.println("its integer"); } } System.out.println((System.nanoTime()-starttime));
有没有任何指南,哪一个使用getClass()
或instanceOf
?
给定一个场景:我知道确切的类匹配,即String
, Integer
(这是最后一类),等等
是使用instanceOf
运算符不好的做法?
instanceof
和getClass() == ...
的性能不同的原因是它们做了不同的事情。
-
instanceof
testing左侧(LHS)的对象引用是右侧(RHS) 还是某个子types的实例。 -
getClass() == ...
testingtypes是否相同。
因此,build议忽略性能问题,并使用替代scheme,为您提供所需的答案。
是的,过度使用它们是“devise气味”。 如果你不小心,最终会有一个devise,在这个devise中添加新的子类会导致大量的代码重新工作。 在大多数情况下,首选方法是使用多态。
(有例外,一个典型的例子是在equals(Object)
的实现中,你需要testing参数的types,如果不匹配的话返回false
,在这种情况下,你通常需要使用getClass()
在子类中正确地实现equals
的合约。)
你想完全匹配一个类,例如只匹配FileInputStream
而不是FileInputStream
的任何子类? 如果是这样,请使用getClass()
和==
。 我通常会在equals
做这个事情,所以X的一个实例并不等于X的一个子类的实例 – 否则你可能会陷入棘手的对称性问题。 另一方面,对于比较两个对象是同一个类而不是一个特定类的情况,通常更有用。
否则,使用instanceof
。 请注意,对于getClass()
您需要确保您有一个非null的引用,否则您将得到一个NullPointerException
,而如果第一个操作数为null,则instanceof
将返回false
。
就个人而言,我认为instanceof
更习惯 – 但在大多数情况下,使用其中任何一种都是一种devise气味。
我知道这已经有一段时间了,但是我昨天学到了另外一种select
我们都知道你可以这样做:
if(o instanceof String) { // etc
但是如果你不知道究竟是什么types的话呢? 你不能一般地做:
if(o instanceof <Class variable>.getClass()) {
因为它给编译错误。
相反,这是一个替代 – isAssignableFrom()
例如:
public static boolean isASubClass(Class classTypeWeWant, Object objectWeHave) { return classTypeWeWant.isAssignableFrom(objectWeHave.getClass()) }
getClass()的约束条件是对象只与同一类的其他对象相同,运行时types相同,如下面的代码所示:
class ParentClass{ } public class SubClass extends ParentClass{ public static void main(String []args){ ParentClass parentClassInstance = new ParentClass(); SubClass subClassInstance = new SubClass(); if(subClassInstance instanceof ParentClass){ System.out.println("SubClass extends ParentClass. subClassInstance is instanceof ParentClass"); } if(subClassInstance.getClass() != parentClassInstance.getClass()){ System.out.println("Different getClass() return results with subClassInstance and parentClassInstance "); } } }
输出:
子类扩展了ParentClass。 subClassInstance是instanceof ParentClass。
不同的getClass()返回带有subClassInstance和parentClassInstance的结果。