Rules for Polymorphism
About
Polymorphism in Java is governed by a set of rules that vary depending on whether it is compile-time (method overloading) or runtime (method overriding). Below is a consolidated set of rules for both types.
Rules for Compile-Time Polymorphism (Method Overloading)
Rule
Example
Valid / Invalid
Reason
Same method name
void print() {}
void print(String msg) {}
Valid
Overloaded methods must share the same name.
Different parameter list
void sum(int a, int b) {}
void sum(double a, double b) {}
Valid
Changing type/number/order of parameters allows overloading.
Return type alone not enough
int getData() {}
String getData() {}
Invalid
Compiler cannot differentiate only by return type.
Different access modifiers allowed
public void show(int x) {}
private void show(String y) {}
Valid
Access modifiers do not affect method signature.
Different exceptions allowed
void read() throws IOException {}
void read(String s) throws SQLException {}
Valid
Exception type does not affect overloading.
Inheritance overloading
class Parent { void show(int x) {} }
class Child extends Parent { void show(double x) {} }
Valid
Overloading works across parent-child classes if parameters differ.
Varargs overloading
void display(String... items) {}
void display(String item) {}
Valid
Varargs can overload fixed parameters, but must be last.
Static / final methods can be overloaded
static void log(int x) {}
static void log(String y) {}
Valid
Static/final methods are still matched at compile time.
Compile-time resolution
public class Problem1 {
static void test(int x) {
System.out.println("x");
}
static void test(long y) {
System.out.println("y");
}
public static void main(String[] args) {
test(5); //x
test(5L); //y
}
}
Valid
Compiler picks best match based on argument type.
Ambiguity causes compile error
public static void main(String[] args) {
doSomething(5, 5); // Ambiguous method call. Both error
}
static void doSomething(int x, long y) {
System.out.println("x");
}
static void doSomething(long x, int y) {
System.out.println("y");
}
Invalid
Compiler cannot decide; both match equally well.
Rules for Runtime Polymorphism (Method Overriding)
Rule
Example
Valid / Invalid
Reason
Must be in inheritance hierarchy
class Parent { void show() {} }
class Child extends Parent { void show() {} }
Valid
Overriding requires a parent-child relationship.
Same method signature
void display(int x)
in Parent and Child
Valid
Method name, parameters, and order must match exactly.
Return type must be same or covariant
Parent: Object getData()
Child: String getData()
Valid
Covariant return types allowed (narrower type in subclass).
Access level cannot be more restrictive
Parent: public void show()
Child: protected void show()
Invalid
Cannot reduce visibility in overriding method.
Can increase access level
Parent: protected void show()
Child: public void show()
Valid
Visibility can be widened in overriding method.
Cannot override static methods
Parent: static void print()
Child: static void print()
Invalid (this is hiding, not overriding)
Static methods belong to the class, not object.
Cannot override final methods
Parent: final void show()
Invalid
Final methods cannot be changed in subclass.
Cannot override private methods
Parent: private void secret()
Invalid
Private methods are not inherited.
Overridden method can throw fewer/narrower checked exceptions
Parent: void read() throws IOException
Child: void read()
Valid
Checked exceptions can be reduced or removed.
Dynamic method dispatch occurs at runtime
Parent p = new Child(); p.show();
Valid
JVM decides which method to call based on object type, not reference type.
Last updated