morgancodes
morgancodes

Reputation: 25265

instanceof yields inconsistent results for detecting interfaces?

Is there anything tricky I should know about instanceof? I'm passing a list of objects through a few methods and testing whether these objects implement a particular interface using instanceof. In some cases, instanceof correctly identifies objects as implementing the interface, in other cases it doesn't. It appears to be giving me inconsistent results on the same object in different places. Is there any trick/gotcha I should be aware of here?

In anticipation of comments you might have:

1) I know instanceof is bad form. I'm working with a less-than-perfect object hierarchy that can't be changed, and this is the least bad thing I can think to do.

2) I'm working to create a code example, but I'll need to simplify my code a lot if I'm going to paste in anything useful here. In the meantime, if you've seen this before and can shed some light, please do.

Upvotes: 12

Views: 8526

Answers (6)

morgancodes
morgancodes

Reputation: 25265

Ok, problem solved. As usual, the problem was less wierd than I thought. The project I'm working on is in the unfortunate condition of having some duplicate class names. I was creating the class using foo.MyInterface and testing for instance of bar.MyInterface. Thanks for the responses. It really did help me think it through.

Upvotes: 9

siddhadev
siddhadev

Reputation: 16631

As long as you have no classloading problem, instanceof works consistently. I guess you know A instanceof B returns true if the A is inherited from B, or some of the interfaces A implements or classes A extends, are instanceof B.

If you get false when you expect true, you probably are trying to compare instances comming from different ClassLoaders.

Upvotes: 3

Tom Hawtin - tackline
Tom Hawtin - tackline

Reputation: 147164

instanceof always returns false for null. It does not compile if it would be impossible for the static type on the left cannot be an instance of the specified type. Other than that, it should work without surprise.

Unlike C++ (and I believe Smalltalk), an object cannot change type at runtime. In C++ the type changes during construction, so that methods cannot be called from a constructor to derived class [subclass] methods.

Upvotes: 9

Todd R
Todd R

Reputation: 18516

You may be wanting "isAssignable" instead of instanceof:

if (MyInterface.isAssignableFrom(myObject.getClass())) {
  //  do work here
}

This will return true for classes that implement your interface.

Upvotes: 0

Jon Skeet
Jon Skeet

Reputation: 1500923

Are you loading any types dynamically, potentially from different classloaders? The only time I've seen apparently inconsistent results was when I had two lines of code which look like they refer to the same type, but which have actually loaded that type from different classloaders.

Upvotes: 14

cadrian
cadrian

Reputation: 7376

The only gotcha I know of is that null is instanceof no type.

Upvotes: 5

Related Questions