• Post Reply Bookmark Topic Watch Topic
  • New Topic

still not clear with polymorphism  RSS feed

 
Punit Jain
Ranch Hand
Posts: 1085
3
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi All,

it seems to be a very basic java question but i am really getting confused here.
this is what i understood via books/tutorials/articals about polymorphism/dynamic polymorphism.

a quick example :



questions :
-----------
1.> why i can't use the simple class initialization, why i need static polymorphism? how it helps?
2.> in lots of books/internet i read it is the good way of doing things, it is good approach bla bla bla.... but in practical really i still don't understand how it is good?
3.> please give me some examples.


now lets's move to dynamic polymorphism
-------------------------------------------------
let's keep the Account, SavingAccount, CurrentAccount class same.
below is the new implementation of ImplAccount



and a new class Decision.java




questions:
----------

1.> what is difference between static and dynamic polymorphism here? still i am creating the instace of SavingAccount. we just added a new class here. how it is becoming dynamic?
2.> what's wrong if instead of writing a new class Decision.java i could put conditions in ImplAccount.java itself only? like this:



i really need some deep understanding here.

 
K. Tsang
Bartender
Posts: 3648
16
Firefox Browser Java Mac OS X
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Simple answer to the difference between static and dynamic polymorphism is at compile time. When the compiler knows what class it is then this is called "static" polymorphism. On the other hand if the compiler does not know what class it is then it's "dynamic", the class is known at run time.

Your examples do show the importance of polymorphism already. Regarding your questions: one obvious advantage to using polymorphism instead on simple initialization is you only need to change one line and everything else still works. If simple initialization then you would need to change every line that contains the class (XXXAccount in your examples).

Hope this helps.
 
Punit Jain
Ranch Hand
Posts: 1085
3
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Thanks Tsang.

Okay so by first statement you meant:-

Account ac = new CurrentAccount()

above would be static/compile time polymorphism as compiler knows what class needs to be instantiated, correct?

i am confused here with dynamic polymorphism, my code was this:





question is here also ImplAccount knows that it needs to instantiate SavingAccount class.

or am i taking it in a wrong way and is should take it in below way?

like i created a new class Decision to remove the direct interaction of main class (ImplAccount) with other classes (SavingAccount,CurrentAccount).
and now at compile time decision class does not know which class to instantiate as we are passing classname to invokeMyAccount() as an argument? and classes getting linked to each other at run time?

 
K. Tsang
Bartender
Posts: 3648
16
Firefox Browser Java Mac OS X
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Punit Jain wrote:



question is here also ImplAccount knows that it needs to instantiate SavingAccount class.

or am i taking it in a wrong way and is should take it in below way?

like i created a new class Decision to remove the direct interaction of main class (ImplAccount) with other classes (SavingAccount,CurrentAccount).
and now at compile time decision class does not know which class to instantiate as we are passing classname to invokeMyAccount() as an argument? and classes getting linked to each other at run time?



Ok the above code is classified as dynamic because the invokeMyAccount() method takes in a Account class, not a SavingAccount or CurrentAccount or XXXAccount. At compile time, the compiler does not know what subclass this will be. At run time, you call this method with SavingAccount and at this point the JDK knows "oh this is a SavingAccount class, let me (JDK) check if this is a Account... yes pass).
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Also,



would be dynamic polymorphism/dynamic binding, not static polymorphism.

Method overloading would be an example of static polymorphism in Java.

 
Punit Jain
Ranch Hand
Posts: 1085
3
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
i see, quite clear to me.

just one more question, what are the advantages of this (dynamic polymorphism)?

also one confusion, method overriding also comes into dynamic polymorphism.
So both "Method overriding" and "initializing an object in such a way that at compile time it cannot predict the class it needs to instantiate (the one i did in my example)" make the polymorphic behavior, correct?
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Punit Jain wrote: "initializing an object in such a way that at compile time it cannot predict the class it needs to instantiate (the one i did in my example)"


I think object initialization never happens at compile time. It's a run time thing.
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
By the way, have you checked the Javaranch campfire stories?

There's an interesting story called 'How My Dog learned Polymorphism', that might give some more clarity on the subject.
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Chan Ag wrote:
Punit Jain wrote: "initializing an object in such a way that at compile time it cannot predict the class it needs to instantiate (the one i did in my example)"


I think object initialization never happens at compile time. It's a run time thing.


Unless if it's a compile time constant.
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Chan Ag wrote:Also,



would be dynamic polymorphism/dynamic binding, not static polymorphism.

Method overloading would be an example of static polymorphism in Java.



Too many responses, I know. Sorry but this is important. Hence, one more thing.

If the withDraw() method was a final method in the Account class, that would still be static polymorphism. This is because the compiler would have had all the information at compile time to resolve the method call.
 
Rico Felix
Ranch Hand
Posts: 411
5
IntelliJ IDE Java Linux
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
One area where polymorphism becomes clear is by using the illustration of a drawing application...

Keeping it simple the application draws shapes... you have the following shapes: Circle, Square, Rectangle

You model all shapes from a base class Shape that has draw() and reDraw() methods are follows:


You extend this class and override the methods for the respective shapes...

Now you have a class lets say Canvas that actually draws the shapes and has a method to re-draw all the shapes at once reDrawAll(Shape[])

The class is as follows:


The benefit of this is that the method is general enough to handle all shapes of the system even if later you introduce new shapes which makes the application extensible as opposed to if you write type specific methods such as:


If you write this type of code and you add four more shapes to the system now you're going to have to add new type specific methods for each new shape

Polymorphism brings extensibility to your application with ease...
 
Campbell Ritchie
Marshal
Posts: 56529
172
  • Likes 2
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Chan Ag wrote: . . .
I think object initialization never happens at compile time. It's a run time thing. . . .

Unless if it's a compile time constant.
I think (not certain: check the Java® Language Specification) the only objects which can count as compile‑time constants are Strings; even they are not initialised until runtime, but they are initialised early at runtime, when the classes are loaded. If you examine the bytecode with javap MyClass -c you find the details of the Strings in the .class file. But they do not actually exist as objects beffore the runtime starts.

Many of us, myself included, think “compile‑time polymorphism” is a contradiction in terms and never say it.
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Actually, wow. I also felt that the compile time polymorphism was a bogus thing - at least from what I know of it -. Good to know that there are others also who felt like that.

About the initialisation of compile time constant Strings, I think that you are right also because
allocating memory to something cannot really happen at compile time. A JVM has to do that.
And initialisation must include memory allocation. Several programs are compiled in one machibe and executed in another.

Thanks for the correction, Campbell. Actually honestly speaking, I had a vague thought at the back of my mind
after posting that thing about compile time constants but I didn't think of it for long enough to correct what I had stated.
But I wouldn't be sure, had you or someone else not mentioned it.

Edit : Sorry Campbell, I can't quote your post right now from my phone.
 
Winston Gutkowski
Bartender
Posts: 10575
66
Eclipse IDE Hibernate Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Campbell Ritchie wrote:Many of us, myself included, think “compile‑time polymorphism” is a contradiction in terms and never say it.

Count me among the "many".

Winston
 
Chan Ag
Rancher
Posts: 1090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Actually I should also add this.

In an eatlier post I said that if the withDraw() method was a final method in the Account class,
it would be an example of static/compile time polymorphism.

But I think the right thing to say is that there would be no polymorphism in that case.
 
Rico Felix
Ranch Hand
Posts: 411
5
IntelliJ IDE Java Linux
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
The only polymorphic behavior that happens at compile-time would be when methods are overloaded... seeing that the compiler binds the method call during compilation which makes it polymorphic statically (the method can act differently based on it signature)... Every thing else with the exclusion of the primitive types would be considered dynamic since the data objects would be placed on the free store/heap which is dynamically allocated memory managed by the programmer or in the Java sense by the Garbage Collector
 
Campbell Ritchie
Marshal
Posts: 56529
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
As I said earlier, I wouldn't call that polymorphic myself. More confusion arises if there are overloaded methods whose arguments are ambiguous. For example, it is difficult to predict which of the following methods is called for each of the four calls, unless you know the rather complicated rules for overloading:-And if you really want to get confused, try making methods static and trying to override them (it is actually impossible, but you can get dangerous confusion).
 
Rico Felix
Ranch Hand
Posts: 411
5
IntelliJ IDE Java Linux
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I would argue that they can still act polymorphic-ally according to the argument passed in during method invocation... All that is required is knowing the steps that the compiler would take to resolve the invocations...

As in with your examples

myObj.foo("Campbell"); would call the String method

myObj.foo(null); would call the String method as its more specific than Object

myObj.foo(123); would call the Object method according to the rules of boxing and upcasting

myObj.foo(new Object()); would call the Object method as its more specific than Object...

These are polymorphic behavior as the method would seem to have many forms using just one name

As for static methods they cannot be overridden as they are bound to the class in which they are defined and can only be overloaded in the class itself or hidden in the subclass

Once you learn the rules the distinguished behavior can be easily understood
 
Campbell Ritchie
Marshal
Posts: 56529
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
All correct but:-This is when the rules about which method version is called get confusing, and when you can make dangerous errors. And what about when you create instances of different classes depending on user input?
Solution:
  • 1: You can't override static methods: don't try.
  • 2: Always call static methods on the name of the class, not the name of the object reference.
  •  
    Rico Felix
    Ranch Hand
    Posts: 411
    5
    IntelliJ IDE Java Linux
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Once you declare a variable or a method as being static it springs into being as soon as the class gets loaded and strives in memory until the class is unloaded or when the application terminates... this happens because the static entity is placed in the static storage class area in memory which is unaffected by object creation which happens in dynamic memory (free store/heap) hence the reason it is bound to the class and cannot be overridden by another class file...
     
    Winston Gutkowski
    Bartender
    Posts: 10575
    66
    Eclipse IDE Hibernate Ubuntu
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Rico Felix wrote:These are polymorphic behavior as the method would seem to have many forms using just one name..

    OK, but when/how would you use that "poly' behaviour?

    And what's to stop it from being completely different because of the type of argument? An action(String) might have a completely different meaning from an action(List), even if they both return an int

    But in real polymorphism, the name defines the behaviour - it's just implemented differently on different subtypes.

    Winston
     
    Rico Felix
    Ranch Hand
    Posts: 411
    5
    IntelliJ IDE Java Linux
    • Likes 1
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Winston Gutkowski wrote:OK, but when/how would you use that "poly' behaviour?


    I would say that it can be used in the same sense as you would use a dynamically invoked method on a limited scale due to early-binding restrictions...

    Example:



    Here we use the name choice polymorphic-ally based on a condition

    Winston Gutkowski wrote:
    And what's to stop it from being completely different because of the type of argument? An action(String) might have a completely different meaning from an action(List), even if they both return an int

    But in real polymorphism, the name defines the behaviour - it's just implemented differently on different subtypes.


    What's to stop overridden methods from being completely different? An object that implemented an interface with the method action(String) would have completely different meaning from another object implementing the same interface... One could be used to change the background color of a window while the other could be used to send a request to a server...
     
    Winston Gutkowski
    Bartender
    Posts: 10575
    66
    Eclipse IDE Hibernate Ubuntu
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Rico Felix wrote:I would say that it can be used in the same sense as you would use a dynamically invoked method on a limited scale due to early-binding restrictions...

    OK, I'll grant you that one; and I have to admit having written code like that myself. Just never really thought of it as "polymorphic".

    What's to stop overridden methods from being completely different?

    Well, for one thing, the language rules. How many times have we seen beginners write:
    public boolean equals(SomeType obj) { ...
    and ask why their class isn't working.

    And sure, you can put any legal code you like in a method, but one would assume that you're overriding for a reason. Otherwise you're just shooting yourself in the foot.

    Winston
     
    Punit Jain
    Ranch Hand
    Posts: 1085
    3
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    OK so all story is about compile time and run time
    if i know it is happening at compile time (mean compiler is aware at the time of compilation only), would be static polymorphism.
    if if it's happening at run time, would be dynamic polymorphism.


    BTW : any good book or text for reading about what all happens at compile time and what all happen at run time (in depth)?

    Thanks,
    Punit
     
    Campbell Ritchie
    Marshal
    Posts: 56529
    172
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Winston Gutkowski wrote: . . . How many times have we seen beginners write:
    . . .
    I suspect there are teachers who don't know why that is wrong.
     
    • Post Reply Bookmark Topic Watch Topic
    • New Topic
    Boost this thread!