| Code | Effect |
|---|---|
| dog instanceof Dog | true |
| dalmatian instanceof Dog | true |
| dog instanceof Dalmatian | false |
| dalmatian instanceof ShowDogInterface | true |
| dalmatian instanceof dog | syntax error |
| ! dalmatian instanceof Dog | syntax error |
| ! (dalmatian instanceof Dog) | false |
| dog instanceOf Dalmatian | syntax error |
| dalmatian instanceof Dog | syntax error |
| dalmatian instanceof Class.forName (DogPackage.Dog ) | syntax error |
| null instanceof String | false |
if ( Class.forName ( classNameString ).isInstance ( myObject ) ) ...Just to keep you on your toes, there are yet other methods with similar names, java.beans.Beans.isInstanceOf and java.beans.Beans.getInstanceOf.
It turns out that everything depends on the type of the desired instance and the actual type of the object. The type of the object’s reference is irrelevant, though obviously it could be used to optimise away silly instanceofs such as Dog instanceof Dog.
One technique is to assign class numbers by walking the inheritance tree of Object depth first. Then all descendants of a given object fall in a range m to n, and no other classes fall in that range. The problem comes when a new class is loaded, especially via Class.forName which would upset the numbering scheme. Perhaps it could leave holes for new classes to fit in. Only rarely would a complete renumbering be needed.
Another brute force technique is to compare the test object’s class with the desired class. If that fails, compare the superclass, etc, right on back to Object.
Here is yet another technique: I want to know if a given Dog reference is a Dalmatian. We know that class nesting depth works like this:
| depth | class name |
|---|---|
| 3 | MostlyBlackDalmatian |
| 2 | Dalmatian |
| 1 | Dog |
| 0 | Object |
For interfaces, it is more complex since classes can implement multiple interfaces. Interfaces can inherit from other interfaces, and classes inherit the interfaces implemented by their ancestors. This is one reason why you attempt to use class references rather than inferface references in time critical code. There you need a bit map indexed by interface number for each class to say whether it implements the interface.
One trick is to cache the class of the last object for which this particular instanceof was called. Chances are good that the next time the Object in question will have the same class. This works for both classes and interfaces.
Initially, Java used a rather flat-footed implementation of instanceof. Further, you also paid quite a penalty for invoking a method via an interface reference rather than a class reference. Over the years, the implementation has become cleverer, first through caching and later reputedly through even cleverer techniques, though I have not seen an essay exactly on how it now works. Further the Jet optimising compiler, using static compile-time analysis can narrow down the possible classes for an object, sometimes down to one, thus bypassing the need for any run time work.
|
|
available on the web at: |
http://mindprod.com/jgloss/instanceof.html |
optional Replicator mirror
|
J:\mindprod\jgloss\instanceof.html | |
![]() |
Please email your
feedback for publication,
letters to the editor, errors, omissions, typos, formatting errors, ambiguities, unclear
wording, broken/redirected link reports, suggestions to improve this page or comments to
Roedy Green :
| |
| Blog | Canadian
Mind
Products
IP:[65.110.21.43] Your face IP:[184.73.74.47] |
|
| Feedback | You are visitor number 538,858. | |