Assignment compatibility is a key concept in Java. It may sound daunting at first, but I promise it isn’t. Basically, it comes down to this:
- Is the thing you want to assign the same type as the thing you want to assign to? Or, if not, then at least
- Is the thing you want to assign guaranteed to have all the properties of the thing you want to assign to?
We’ve already covered this when we looked at inheritance.
Suppose I have a CollegeStudent class that extends Student.
Then, I can always say
Student s = new CollegeStudent();
because every CollegeStudent is a Student because CollegeStudent
extends Student.
CollegeStudent objects, because of this “extends” relationship
(thought of as “is a”), have all the properties of a Student, so the assignment
of a CollegeStudent object into a Student reference is perfectly legal. There
is nothing in a Student that is not also present in a CollegeStudent. A CollegeStudent
may have more than just a Student, but it has at least all the properties and behaviors
of a Student.
There, of course, exists a trivial case of this.
You can always say that Object o = new CuteFluffyPony();
because every CuteFluffyPony by definition is an Object because every
class implicitly extends Object.
An example of an assignment that would not be legal
would be the following:
suppose:
Bird extends Animal
and also that
Cat extends Animal
Bird myBird = new Cat();
Bird objects and Cat objects are both Animal objects, but Birds and Cats do not
have a relationship like Students and CollegeStudents do. Birds and Cats are,
at best, siblings, so there is no guarantee that all the promises of a Bird are fulfilled in
a Cat, so this assignment (or the reverse, Cat myCat = new Bird();) are always
illegal.
In other words, an assignment is legal if:
- The left and right object types are the same or, if not
- The right object type is a sibling of the left object type, such that the right and left objects (in that direction) are perfectly interchangeable
It is perfectly legal to declare
List<T> myList = new ArrayList<>();
just as it is perfectly legal to declare
List<T> myList = new LinkedList<>();
because every LinkedList is, by definition, a List, and every
ArrayList is also by definition a List. Since the type on the right fulfils all
the conditions of the type on the left, even though they’re different, the assignment
is always perfectly legal.
No comments:
Post a Comment