Java Reference
In-Depth Information
Here, we iterate through the list of posts (held in an
ArrayList
in the
posts
variable). We get
out each post and then invoke its
display
method. Note that the actual posts that we get out
of the list are of type
MessagePost
or
PhotoPost
, not of type
Post
. We can, however, use
a loop variable of type
Post
, because variables are polymorphic. The
post
variable is able to
hold
MessagePost
and
PhotoPost
objects, because these are subtypes of
Post
.
Thus, the use of inheritance in this example has removed the need for two separate loops in the
show
method. Inheritance avoids code duplication not only in the server classes, but also in
clients of those classes.
Note
When doing the exercises, you may have noticed that the
show
method has a problem: not
all details are printed out. Solving this problem requires some more explanation. We will provide this
in the next chapter.
Exercise 8.14
What has to change in the
NewsFeed
class when another
Post
subclass
(for example, a class
EventPost
) is added? Why?
8.7.5
Casting
Sometimes the rule that we cannot assign from a supertype to a subtype is more restrictive than
necessary. If we know that the supertype variable holds a subtype object, the assignment could
actually be allowed. For example:
Vehicle v;
Car c = new Car();
v = c; // correct
c = v; // error
The above statements would not compile: we get a compiler error in the last line, because as-
signing a
Vehicle
variable to a
Car
variable (supertype to subtype) is not allowed. However,
if we execute these statements in sequence, we know that we could actually allow this assign-
ment. We can see that the variable
v
actually contains an object of type
Car
, so the assignment
to
c
would be okay. The compiler is not that smart. It translates the code line by line, so it looks
at the last line in isolation without knowing what is currently stored in variable
v
. This is called
type loss. The type of the object in
v
is actually
Car
, but the compiler does not know this.
We can get around this problem by explicitly telling the type system that the variable
v
holds a
Car
object. We do this using a
cast operator
:
c = (Car) v; // okay
The cast operator consists of the name of a type (here,
Car
) written in parentheses in front of a vari-
able or an expression. Doing this will cause the compiler to believe that the object is a
Car
, and it
will not report an error. At runtime, however, the Java system will check that it really is a
Car
. If
we were careful, and it is truly is a
Car
, everything is fine. If the object in
v
is of another type, the
runtime system will indicate an error (called a
ClassCastException
), and the program will stop.
3
3
Exceptions are discussed in detail in Chapter 12.
Search WWH ::
Custom Search