Compile-time types
Run-time types and polymorphism
Constructor protocol
Private variables
When you declare a variable you are saying what kinds of values that variable can hold.
This also limits what you can do with that variable to only those things that you can do with that type.
public class Animal {
public void feed() { … }
}
public class Dog extends Animal {
public void walk() { … }
}
We can feed any kind of animal.
But we can only walk dogs.
Animal critter = …;
Can we walk whatever’s in this crate?
Dog critter = …;
How about what’s in here?
Animal animal = new Dog("Fido");
The compiler will check that Dog is a subclass of
Animal to make sure this is a safe assignment.
But it can't keep track of what animal really is.
You've told it it’s an Animal so that's all it keeps
track of.
Animal animal;
if (Math.random() < 0.5) {
animal = new Dog("Fido");
} else {
animal = new Rhinoceros();
}
The compiler can check that both Dog and
Rhinoceros are subclasses of Animal so
either assignment is safe.
But there’s no point trying to guess what animal is
going to be beyond an Animal.
animal.walk()
No.
The compiler only knows that animal is an
Animal and Animal doesn’t have a
walk method.
The compiler just makes sure that every method call is legal. I.e.
if we call animal.feed() there will be some
feed method.
But once a program is running, the run-time type of the object, i.e. what class was actually used to construct the object, will determine which code is run.
Any method call to an non-static method can be thought of as sending a message to that object saying, “Do the thing.”
This is the essence of polymorphism. How any given object will respond to that message is determined by the actual class of the object, not by what the compiler knows about its type.
public class Eater {
public void eat(Food food) {
System.out.println("Nom nom nom.");
}
}
public class PickyEater extends Eater {
public void eat(Food food) {
System.out.println(isFavorite(food) ? "Yum" : "Yuck!");
}
}
Eater eater = someKindOfEater();
Compiler knows eater is an Eater. So this
is safe:
eater.eat(new Broccoli());
But at runtime it will be some particular kind of eater.
That runtime type will determine which
eat method is called.
public class Dog {
public void act() {
System.out.println("run ");
eat(); // this is still a polymorphic call
}
public void eat() {
System.out.println("eat ");
}
}
The call to eat in act may run the method
defined in Dog or it may not.
super.method()This is not a polymorphic call. It always invokes the method found in the direct parent class of the class containing the call.
public class A {
public void foo() {...}
}
public class B extends A {
public void bar() {
super.foo(); // always invokes A's foo
foo(); // invokes foo from actual class of object
}
public void foo() {...}
}
public class C extends B {
public void foo() {...}
}
“You have the right to a constructor. If you do not do not write a constructor, one will be provided for you.”

All classes must have at least one constructor.
If you do not write a constructor, the compiler will add a no-argument constructor for you.
All constructors must, as the first thing they do, invoke a constructor from their parent class.
If a constructor does not explicitly invoke a parent constructor
with super, the compiler will insert a call to
super(), i.e. to a no-argument constructor.
A constructor in a class whose parent class does not have a no-arg constructor must explicitly invoke one of the constructors the parent class does have.
When extending a class without a no-arg constructor you will have to write a constructor in order to invoke one of the parent's constructors.
Remember that the job of a constructor is to make sure an object is properly initialized and ready to use.
These rules work to ensure that that stays true even in the face of inheritance.
Not much to say here. private means private.
Subclasses can not directly reference private variables
from their parent class.
Note that you can even have a variable in a subclass that is the same name as a private variable in the superclass. In such a case they are different variables.