Reputation: 355
I know that overloading is done at compile time because number and type of arguments are specified and compiler knows which one method in object was called.
But in overriding why doesn't the compiler see whether a subclass method exist in superclass or not?
If the compiler do not know about classes at the compile time then how does it recognize overloading?
thanks!
Upvotes: 5
Views: 1375
Reputation: 691715
Put yourself in the shoes of the compiler. Imagine you must compile the following method:
public void foo(List<String> list) {
System.put.println(list.size());
}
How could you possibly know what the concrete type of list
is, and thus which concrete implementation of the size()
method to call? Is it an ArrayList? A LinkedList? A CopyOnWriteArrayList? You can't know.
If you're not convinced yet, the caller of the method could do something like
if (Math.random() > 0.5) {
foo(new ArrayList<>());
}
else {
foo(new LinkedList<>());
}
There is no way to know at compile-time what the concrete type of the list is. You can only know at runtime. So which of the size()
method is being called can only be decided at runtime.
Upvotes: 13
Reputation: 271150
Overriding is checked at compile time!
Look at this:
class Base {
public void myMethod() {}
}
class Derived extends Base {
@Override // error!
public void myMethod2() {}
}
The compiler checks whether myMethod2
is in the base class, which it isn't, so the compiler gives an error.
However, deciding which version of an overridden method to call is determined at runtime. This is because to determine which method to call, the runtime type of the object must be known. The compiler cannot know the runtime type of a variable unless it runs your code, at which point it's not "compile"-time anymore...
Look at this:
class Base {
public void myMethod() {}
}
class Derived extends Base {
@Override
public void myMethod() {}
}
// ...
Base obj;
if (Math.random() > 0.5) {
obj = new Derived();
} else {
obj = new Base();
}
obj.myMethod();
Proof by contradiction:
If the version of the method to call is decided at compile time, then the myMethod()
call here will always call the same version of the method at runtime, no matter how many times you run the code. But from the if statement, we can see that the method to call changes depending on a condition. But this condition varies between different runs of the code. This creates a contradiction, so the version to call must be determined at runtime. QED :).
Upvotes: 4