Welcome Message

Hi, welcome to my website. This is a place where you can get all the questions, puzzles, algorithms asked in interviews and their solutions. Feel free to contact me if you have any queries / suggestions and please leave your valuable comments.. Thanks for visiting -Pragya.

January 18, 2010

Polymorphism in Overloaded and Overridden Methods

How does polymorphism work with overloaded methods? From what we just looked at, it doesn't appear that polymorphism matters when a method is overloaded. If you pass an Animal reference, the overloaded method that takes an Animal will be invoked, even if the actual object passed is a Horse. Once the Horse masquerading as Animal gets in to the method, however, the Horse object is still a Horse despite being passed into a method expecting an Animal. So it's true that polymorphism doesn't determine which overloaded version is called; polymorphism does come into play when the decision is about which overridden version of a method is called. But sometimes, a method is both overloaded and overridden. Imagine the Animal and Horse classes look like this:

public class Animal {
public void eat () {
System.out.println("Generic Animal Eating Generically"};
}
}
public class Horse extends Animal {
public void eat() {
System.out.println("Horse eating hay ");
}
public void eat(String s) {
System, out .println ("Horse eating " + s) ;
}
}

Notice that the Horse class has both overloaded and overridden the eat() method. Table 2-2 shows which version of the three eat() methods will run depending on how they are invoked.

Table 2-2: Examples of Illegal Overrides Method Invocation Code
Result

Animal a = new Animal(); a.eat();
Generic Animal Eating Generically

Horse h = new Horse(); h.eat();
Horse eating hay

Animal ah = new Horse (); ah.eat();
Horse eating hay

Polymorphism works—the actual object type (Horse), not the reference type (Animal), is used to determine which eat() is called.

Horse he = new Horse(); he.eat("Apples") ;
Horse eating Apples

The overloaded eat(String s) method is invoked.

Animal a2 = new Animal(); a2.eat ("treats");
Compier error! Compiler sees that Animal class doesn't have an eat() method that takes a String.

Animal ah2 = new Horse(); ah2.eat("Carrots");
Compiler error! Compiler still looks only at the reference, and sees that Animal doesn't have an eat() method that takes a String. Compiler doesn't care that the actual object might be a Horse at runtime.




Exam Watch
Don't be fooled by a method that's overloaded but not overridden by a subclass. It's perfectly legal to do the following:

public class Foo {
void doStufff() { }
}
class Bar extends Foo {
void doStuff(String s) { }
}

The Bar class has two dostuff () methods: the no-arg version it inherits from Foo (and does not override), and the overloaded dostuff (string s) defined in the Bar class. Code with a reference to a Foo can invoke only the no-arg version, but code with a reference to a Bar can invoke either of the overloaded versions.

No comments: