Chapter 9 Notes
CSE 4301 (Java)
Inheritance
I. Introduction
A. Java does not support multiple inheritance of classes.
B. But, a Java class can inherit both a class and an interface.
C. A Java class can inherit only one level up; it, then,
becomes the responsibility of the superclass to
inherit it's superclass, etc.
D. A subclass can not directly access the private members of its
superclass.
E. A subclass can directly access the following members of its
superclass, provided it is in the same package as the superclass:
1. public members
2. protected members
3. package access members
NOTE: a class can have members in all three of the above storage
classes
F. A subclass should override a method in it's superclass if:
1. The method is abstract in the superclass
2. The method is only stubbed in the superclass
3. The method's behavior (as defined in the superclass) is inappropriate
for the subclass.
II. Superclasses and Subclasses
A. Inheritance models the "is-a" relationship by using a subclass to
expand the definition of the superclass, thus providing a more
restrictive subset of the objects belonging to the superclass.
1. A boss is an employee.
2. A cylinder is a circle.
3. A circle is a point.
4. A rectangle is a quadrilateral.
B. The "is-a" relationship is not bidirectional. It is not true to
say that a superclass (Employee) is a subclass (Boss).
III. Protected members
A. A superclass's public members are accessible anywhere the program has
a reference to that superclass type or one of its subclass types.
B. A superclass's protected access members may be accessed only by:
1. methods of the superclass
2. methods of subclasses of the superclass
3. methods of other classes in the same package (not true in C++)
NOTE: protected members have package access
C. An explicit cast can be used to convert a superclass reference to a
subclass reference, but only if the superclass reference is actually
referencing a subclass object.
Any attempt to do otherwise will generate a ClassCastException.
IV. Relationship between Superclass Objects and Subclass Objects
A. The subclass must inherit the superclass:
public class Circle extends Point
B. The testing program does not inherit the superclass. It only in-
stantiates objects of the subclasses.
C. A subclass can explicitly pass arguments to it's superclass:
super(a, b);
D. If a subclass does not explicitly call the superclass's constructor,
the default constructor in the superclass is called automatically
at the point where the call to the superclass's constructor should
have been ( super() ).
F. If the subclass does not explicitly call a constructor in the super-
class, and if the superclass does not have a default constructor,
the compiler will generate an error.
G. The call to the superclass's constructor must be the first statement
in the subclass's constructor. Any other location will generate a compile-
time error.
H. If a subclass does not override methods defined in the superclass,
the subclass can expect to use the methods as defined in the
superclass:
JApplet: init(), start(), toString(), paint()
super.init(), super.start(), super.toString(), super.paint()
Normally, a subclass overrides the method as defined in the superclass
by first calling the method in the superclass and then doing some
additional work.
Not using the super reference to call the same method in the superclass
results in infinite recursion because the subclass method actually
calls itself.
The super reference can only be used once per instruction. The following
would generate a syntax error:
super.super.x
********Figure 9.4, Point4.java, p. 391
Circle4.java, p. 391
InheritanceTest4.java, p. 392
V. Constructors and Finalizers in Subclasses
A. Superclass constructors are not inherited by subclasses.
B. If both super and sub classes have a finalize() method, the
subclass finalize() should, if overriding the super's finalize(),
call the superclass's finalize() method as it's last action, for
purposes of garbage collection.
C. Method finalize() in a superclass should always be defined as
protected, to keep classes not inheriting from that class from
having access to that finalize() method.
*********Figure 9.5, Point5.java, p. 398
Circle5.java, p. 398
Test5.java, p. 399
VI. Implicit Subclass-Object-to-Superclass-Object Conversion
A. Subclass objects can be treated as superclass objects (a subclass
"is-a" superclass).
B. An attempt to assign a superclass object to a subclass reference
would leave additional subclass members undefined, and therefore
is a syntax error.
C. There are 4 possible ways to mix and match superclass and subclass
references with superclass and subclass objects:
1. Refer to a superclass object with a superclass reference (normal)
2. Refer to a subclass object with a subclass reference (normal)
3. Refer to a subclass object with a superclass reference
--safe, because the subclass object "is-a" object of the
superclass
-- such code can only refer to superclass members
-- if this code refers to subclass-only members by using the
superclass reference, the compiler will generate a syntax
error
4. Refer to a superclass object with a subclass reference
-- it is not true to say that a superclass "is-a" object of
the subclass
-- will generate a syntax error
-- the subclass reference must first be cast to a superclass
reference
VII. Composition vs. Inheritance ("has-a" vs. "is-a")
*********Figure 9.6, Point6.java, p. 403
Test6.java, p. 403
*********Figure 9.7, Circle7.java, p. 404
Test7.java, p. 404
*********Figure 9.8, Cylinder8.java, p. 407
Test8.java, p. 407
VIII. Introduction to Polymorphism
A. With polymorphism, programs can be written to process generically
(as superclass objects) objects of all existing classes in a
hierarchy.
B. Classes that do not exist during development can be added with little
or no modifications to the generic part of the program, as long as
those classes are part of the hierarchy that is being processed
generically.
IX. Type Fields and switch statements
A. Selecting the appropriate behavior by using a switch statement based
on the type of the object is error-prone:
1. The programmer might forget to make such a type test when one is
warranted.
2. The programmer may forget to test all possible cases in a switch.
3. If a switch-based system is modified by adding new types, the
programmer might forget to insert the new cases in existing
switch statements.
4. Every addition or deletion of a class demands that every switch
statement be modified, which is time consuming and error prone.
B. Polymorphism is the preferred alternative to switch logic, for the
opposite of the reasons listed in IX.A. above.
X. Dynamic Method Binding
A. Assume a superclass called Shape.
B. Assume subclasses called Circle, Triangle, Rectangle, Square, etc.
C. Declare the method draw() in the superclass, as well as in each subclass.
D. If a superclass reference is used to refer to a subclass object,
1. and the draw() method is called via that superclass reference
2. the program will choose the correct subclass's draw() method
at run time--dynamic method binding
3. In C++, the same applies, provided that the functions are virtual
If they are not virtual, the call via the superclass reference would
simply call the function in the superclass, if it is not pure virtual.
XI. final methods and classes
A. Variables can be declared final to indicate that they cannot be
modified after they are declared and that they must be initialized
when so declared.
B. A method that is declared final cannot be overridden in a subclass.
C. Methods that are declared static and methods that are declared
private are implicitly final.
D. The compiler can optimize the program by replacing calls to final
methods with the code in that method's definition (inlining)
XII. Abstract superclasses and Concrete Classes
A. A class for which no objects are to be instantiated can be declared
abstract:
public abstract class X
1. The sole purpose of an abstract class is to provide an appropriate
superclass from which other classes may inherit as an interface and/or
implementation.
2. If a class is not abstract, it is considered to be concrete.
3. Multiple abstract classes can exist in an inheritance hierarchy.
4. An inheritance hierarchy does not have to have any abstract
classes.
XIII. Polymorphism
A. In C++, polymorphism can be accomplished by doing the following in the
context of an inheritance hierarchy:
1. All classes provide at least one function with the same
signature.
2. That function is declared virtual in each class, perhaps even
pure virtual in the base class.
3. A non-member function is called from another non-member function
(virtualViaPointer() from main() ), passing to the first function
a base class reference which had been assigned to a derived class
object.
4. The first function (virtualViaPointer() ) knows to call the
virtual function in the class of which the derived class object
was instantiated, even though the reference was declared to be
of the base class type.
5. If the functions are not virtual, then the polymorphic function
(virtualViaPointer() ) will just call the base class version, if
it is not pure virtual.
B. In Java, polymorphism is accomplished by doing the following in the
context of an inheritance hierarchy:
1. All classes must provide at least one non-final method with the
same signature.
2. A superclass reference is assigned to a subclass object.
3. A method which expects the superclass reference will determine at
run time which subclass of that superclass contains the method to
be executed, and calls that method
4. The same message, sent to a variety of objects, thus takes on
many forms--polymorphism.
5. The programmer can command a wide variety of objects to behave
in manners appropriate to those objects without even knowing
the types of those objects.
XIV. Polymorphism case study
**********Figure 9.9, Employee9.java, p. 414
**********Figure 9.9, Boss.java, p. 415
**********Figure 9.9, CommissionWorker.java, p. 415
**********Figure 9.9, PieceWorker.java, p. 416
**********Figure 9.9, HourlyWorker.java, p. 417
**********Figure 9.9, Test.java, p. 418
XV. Polymorphism case study
**********Figure 9.10, Shape10.java, p. 421
**********Figure 9.10, Point10.java, p. 422
**********Figure 9.10, Circle10.java, p. 422
**********Figure 9.10, Cylinder10.java, p. 423
**********Figure 9.10, Test10.java, p. 424
XVI. Creating and Using Interfaces
A. The abstract superclass can, alternatively, be an interface.
1. An interface definition begins with the keyword interface and
contains a set of public abstract methods and/or public final
static data.
a. An interface containing method prototypes (p. 427)
public interface Shape
{
public abstract double area();
public abstract double volume();
public abstract String getName();
}
b. An interface containing data only (p. 432)
public interface Constants
{
public static final int ONE = 1;
public static final int TWO = 2;
public static final int THREE = 3;
}
2. To use an interface, a class must specify that it implements the
interface.
a. That class must then define every method in the interface
with the exact signature and return type as specified in
the interface definition.
b. If that class leaves one or more methods in the interface undefined,
the class itself becomes abstract and must be declared
abstract in the first line of its class definition.
NOTE: failure to so declare the class abstract will cause
the compiler to generate a syntax error
c. Implementing an interface is like signing a contract with the
compiler that states, "I will define all the methods specified
by the interface."
B. ***********Figure 9.11, Shape.java (an interface), p. 427
***********Figure 9.11, Point11.java, p. 428
***********Figure 9.11, Circle11.java, p. 429
***********Figure 9.11, Cylinder11.java, p. 428
***********Figure 9.11, Test11.java, p. 431
XVII. Inner Class Definitions
A. A class can be defined within another class definition.
1. Such a class can be
a. completely defined, including the class name, or
b. anonymous--having no class name
B. An inner class is used when it has no bearing on the outer class's
interface to external clients.
C. Inner classes are frequently used with GUI event handling.
**********Figure 9.12, Time12.java, p. 433
**********Figure 9.12, TimeTestWindow12, p. 434
D. Compiling a class with inner classes results in a separate .class
file for every class.
1. Inner classes with names have the compiled file name
OuterClassName$InnerClassName.class
2. Anonymous inner classes have the compiled file name
OuterClassName$#.class
where # starts at 1 and is incremented for each anonymous
inner class encountered during compilation.
3. To use the outer class's this reference, use OuterClassName.this
E. The outer class is responsible for creating any objects of its
inner classes.
F. To create an object of another class's inner class, first create an
object of the outer class and assign it to a reference, such as ref.
Then create an inner class object:
OuterClassName.InnerClassName innerRef = ref.new InnerClassName();
G. An inner class can be declared static.
1. A static inner class does not require an object of its outer class
to be defined (but a non-static inner class does).
2. A static inner class does not have access to the outer class's
non-static members.
XVIII. Type-Wrapper Classes for Primitive Types
A. Each of the primitive data types has a type-wrapper class:
type-wrapper class name inherits from
1. Character
2. Byte Number
3. Short Number
4. Integer Number
5. Long Number
6. Float Number
7. Double Number
8. Boolean
B. Each type-wrapper class enables primitive types to be treated as
objects of class Object.
1. Therefore, values of the primitive data types can be processed
polymorphically if they are maintained as objects of the
type-wrapper classes.
C. Each type-wrapper is final
D. Many of the methods that process the primitive data types are
static methods of the type-wrapper classes.
This page was last updated on 05.08.2000.