vibhas karn wrote:@Sam yes sir, the statement is " Any java object that can pass more than one IS-A test can be considered polymorphic. Other than objects of type Object, all java objects are polymorphic in that they pass the IS-A test for their own tupe and for class Object" refer the book by Keithey Sierra for SCJP 1.5 page 95 1st 3 lines. I am really really confused. Please help in two minutes drill on page 154 it is written that polymorphism applies to overriding , not to overloading.Any help please
vibhas,
I am new to Java but lets see if I can take my beginner approach and help you understand. It is my understanding that Polymorphism does apply to overriding. Don't let yourself get confused with overriding and overloading. Overloading simply means that you will have more than one method with the same name in a class. The parameter list must also be different for each method by parameter type. At runtime, your object will decide which method to use based on the arguments passed to the method. For example, overloading consists of having a method named addNums(). The example below shows overloading (taken from Head First Java).
This example shows the same method name addNums but with a different return type and parameters for each method declaration. That is method overloading. Overloading has nothing to do with general concept of polymorphism. Plain and simple!
Overriding and Polymorphism: (examples taken from Head First Java)
Consider a class hierarchy such as Animal -> Canine -> Dog and Wolf. In a general sense, the design of this hiearchy would consist of marking both Animal and Canine classes abstract, including their methods. Why? Well, what does it mean to be an Animal or a Canine? In this design it really doesn't mean anything. We won't want anyone to instantiate an object of type Animal or Canine so we mark them as abstract, meaning you can't "new" up objects. From an inheritance point of view, we can still say that A Dog or Wolf is a Canine and a Canine is an Animal. Any abstract methods from Animal to Canine will need to be implemented in Dog or Wolf since they are the concrete classes. play() isn't implemented as a non-abstract method because how would you tell all generic Canine objects to play? It really would depend on what Canine object you are so you would need to extend from Canine to create more specialized, concrete Canine classes (such as Dog, Wolf, Fox, etc). Please ignore the fact that this may not be the best design. This also means that any methods in Object have now been inherited by Dog and Wolf. Why? Because A Dog or Wolf is a Canine, which is a Animal which is a Object. So imagine that the Dog and Wolf class both have a Play method with their own implementations that they inherited from Canine, which inherited it from Animal. This means that the Dog play method may mean "Ok dog, go roll on your stomach and wag your tail". As for Wolf, this may mean "Ok wolf, go run around in circles and howl". As you can see, each implementation of play means a different thing depending on which class it belongs to. So now, say you were developing an application for animal owners. Lets also say that you developed some method to tell some type of animal to play. This will be the main goPlay() method in your application. Using a polymorphic class type such as Animal will allow you to pass in any concrete subclass of Animal-->Canine and call the play() method specific to that concrete subclass.
In this example, you create a new AnimalOwner object. So imagine you are a proud new owner of a Dog and a Wolf. By using inheritance and abstract classes, we can say "I want a new Animal object, but I want that object to be a new Dog, or a new Wolf". As the owner, you are getting pretty bored so you tell your new animals to goPlay() by passing in the object reference d for Dog and w for Wolf. What happens next is important. You pass these object references to the goPlay method which has a parameter of type Animal. Since a Dog and Wolf is a Canine, which is an Animal you can do this. So when calling this: owner.goPlay(d), you are invoking the play() method for that particular type, which in this case is a Dog. In order for a.play() to work with whatever object reference you passed in, the type of the object reference must implement its own version of play(). This happens because you declared play() in Animal and Canine as abstract. So any concrete class that inherits from Canine will need to implement the play() method. So say you've implemented your application, but now you want to own a Fox and you want to tell it to play. You will "extend" from class Canine, which will require you to implement a play() method. Now when you pass an object reference of type Fox to goPlay, it will treat it as an Animal, which it is due to inheritance and tell the particular Fox to play. As you can see, you'll have a very powerful goPlay method that will allow you to create/extend new types of Animals-->Canines without having to redesign your methods. If you tried to do Canine c = new Canine(); and call owner.goPlay(c), you would receive an exception because you can't create new instances of a Canine. What is a Canine anyways? It is an abstract class and won't allow objects to be created.
In summary, I believe inheritance and polymorphism go hand in hand for a good design. If concrete or abstract classes are foreign to you I recommend you reread this material in your training guide. I'm hoping I didn't confuse you. I tried to explain it as best as I could in a beginner fashion.