The key lies in the behavior of this code, offered by Larry Chung:
If x() in Dog overrides x() in Animal, the output is, "from Dog" as determined by the type of
the object, Dog. But the output is "from Animal" which means the method called was based
on the variable type, Animal. Another clue is the compiler warning about calling a static method
on an instance variable. With proper calling syntax, Animal.x() or Dog.x(), there is no confusion
about overriding versus redefinition.
Jim ...
...