THE Java™ Programming Language, Fourth Edition

(Jeff_L) #1

sup.show();
ext.show();
System.out.println("sup.str = " + sup.str);
System.out.println("ext.str = " + ext.str);
}
}


There is only one object, but we have two variables containing references to it: One variable has type
SuperShow (the superclass) and the other variable has type ExtendedShow (the actual class). Here is the
output of the example when run:


Extend.show: ExtendStr
Extend.show: ExtendStr
sup.str = SuperStr
ext.str = ExtendStr


For the show method, the behavior is as you expect: The actual class of the object, not the type of the
reference, governs which version of the method is called. When you have an ExtendShow object, invoking
show always calls ExtendShow's show even if you access it through a reference declared with the type
SuperShow. This occurs whether show is invoked externally (as in the example) or internally within
another method of either ExtendShow or SuperShow.


For the str field, the type of the reference, not the actual class of the object, determines which class's field is
accessed. In fact, each ExtendShow object has two String fields, both called str, one of which is hidden
by ExtendShow's own, different field called str:


The field that gets accessed is determined at compile time based on the type of the reference used to access it.


Inside a method, such as show, a reference to a field always refers to the field declared in the class in which
the method is declared, or else to an inherited field if there is no declaration in that class. So in
SuperShow.show the reference to str is to SuperShow.str, whereas in ExtendShow.show the
reference to str is to ExtendShow.str.


You've already seen that method overriding enables you to extend existing code by reusing it with objects of
expanded, specialized functionality not foreseen by the inventor of the original code. But where fields are
concerned, it is hard to think of cases in which hiding them is a useful feature.


If an existing method had a parameter of type SuperShow and accessed str with that object's reference, it
would always get SuperShow.str even if the method were actually handed an object of type
ExtendShow. If the classes were designed to use a method instead of a field to access the string, the
overriding method would be invoked in such a case and the ExtendShow.str could be returned. This
hiding behavior is often another reason to prefer defining classes with private data accessed only by methods,

Free download pdf