Java Overloaded AND Overridden Methods

257 Views Asked by At

In the following program, I have one single method in class A overloaded 3 times and then in subclass B, all 3 overloaded methods are overridden.

obj3 is an object with reference type A(superclass) and object type B(subclass) and it calls the method from B on execution, which is expected behavior.

Since overloading and overriding both exist in this code, does that mean that it performed static binding at compile time (to the matching method in class A) and then dynamic binding at run time (to method in class B). Can they both occur together?

My assumption is that this is a classic case of dynamic binding as I believed "binding" is meant to be a permanent action, but a peer suggests that it is both together(static first, then dynamic).

class A{
    
    public void method(Integer n){
        System.out.println("Integer: "+n);
    }
    
    public void method(String s){
        System.out.println("String: "+s);
    }
    
    public void method(String s, Integer n){
        System.out.println("String: "+s+" Integer: "+n);
    }
}

class B extends A{
    
    public void method(Integer n){
        System.out.println("Integer(from B): "+n);
    }
    
    public void method(String s){
        System.out.println("String(from B): "+s);
    }
    
    public void method(String s, Integer n){
        System.out.println("String(from B): "+s+" Integer(from B): "+n);
    }
}

public class Test{
    public static void main(String[] args){
        A obj1 = new A();
        B obj2 = new B();
        A obj3 = new B();
        
        System.out.println("Integer form of method");
        // Integer form of method

        System.out.println("Ref A Obj A");
        // Ref A Obj A
        obj1.method(1);
        // Integer: 1
        
        System.out.println("Ref B Obj B");
        // Ref B Obj B
        obj2.method(2);
        // Integer(from B): 2
        
        System.out.println("Ref A Obj B");
        // Ref A Obj B
        obj3.method(3);
        // Integer(from B): 3
        
    }
}
3

There are 3 best solutions below

5
On BEST ANSWER

Since overloading and overriding both exist in this code, does that mean that it performed static binding at compile time (to the matching method in class A) and then dynamic binding at run time (to method in class B)

Right. The compiler chose the matching signature, and this is static, based on the type of the variable (A in this case).

At runtime, Java finds the implementation of the signature selected by the compiler. This is dynamic, based on the runtime class of obj3 (B, in this case).

0
On

One more attempt to make it clear:

Overloading

Overloading means that a single class has multiple methods with different parameter types (aka. signatures), and you just happened to give them the same name. Your program will work the very same if you change to individual names for the methods, e.g. methodI(Integer n), methodS(String s), and methodSI(String s, Integer n).

Or, you can imagine the compiler to internally always append such a types list to the method name.

Overloading is resolved by the compiler, based on the compile-time types of the parameter expressions.

E.g. if you write

Object par = "Test";
a.method(par);

you get a compiler error. Even though we all see it's a String that you are passing into the method, the compiler only sees an Object, and finds no matching method. Only if you were to introduce an additional method(Object o), the compiler would choose that one. And runtime would call that method and not the String version!

Overriding

Overriding means that at runtime the JVM calls the method implementation depending on the runtime class of the "object before the dot".

And in this case, "method" is to be read as the overloaded method version that the compiler found to match the parameter list. So, runtime already knows whether methodI(), methodS(), or methodSI() is meant, and only decides from which class to take the implementation.

Personal opinion

Allowing multiple methods to share the same name, but differ in parameter lists (aka overloading), produces too much confusion for its benefit.

0
On

You right. Compiler is statically choose between overloads in class A and put that information into .class file in form of method FQN.

Then runtime dynamically choose between implementation of that method.