Method Overloading
Method overloading is a feature in Java that allows a class to have multiple methods with the same name but different parameter lists. It improves code readability, reusability, and flexibility and is a classic example of compile-time polymorphism. This is a very common interview topic.
What Is Method Overloading?
- Same method name
- Different parameter list
- Occurs within the same class (or inherited)
- Resolved at compile time
int add(int a, int b) {
return a + b;
}
int add(int a, int b, int c) {
return a + b + c;
}
Why Method Overloading Is Used
- Improves readability
- Provides logical grouping of related operations
- Allows same action with different inputs
- Reduces method name explosion
Rules of Method Overloading (Very Important)
1. Parameter List Must Be Different
Overloading can differ by:
- Number of parameters
- Type of parameters
- Order of parameters
add(int a, int b)
add(int a, int b, int c)
add(double a, double b)
add(int a, double b)
2. Return Type Alone Cannot Overload a Method ❌
int test() { }
double test() { } // Compile-time error
3. Access Modifiers Do NOT Matter for Overloading
public void show(int a) { }
private void show(double a) { }
✔ Valid overloading
Types of Method Overloading
1. By Number of Parameters
void display() { }
void display(int a) { }
2. By Data Type of Parameters
void display(int a) { }
void display(String a) { }
3. By Order of Parameters
void display(int a, String b) { }
void display(String b, int a) { }
Method Overloading with Type Promotion
Java performs automatic type promotion.
void show(int a) {
System.out.println("int");
}
void show(double a) {
System.out.println("double");
}
show(10); // calls show(int)
show(10.5); // calls show(double)
Ambiguity in Method Overloading
void test(int a, double b) { }
void test(double a, int b) { }
test(10, 10); // Compile-time error (ambiguous)
Method Overloading with String
void print(String s) {
System.out.println("String");
}
void print(Object o) {
System.out.println("Object");
}
print("Java"); // calls String version
Method Overloading with null
void show(String s) {
System.out.println("String");
}
void show(Object o) {
System.out.println("Object");
}
show(null); // calls String (more specific)
Overloading main() Method
Yes, main() can be overloaded.
public static void main(String[] args) {
System.out.println("Main method");
}
public static void main(int a) {
System.out.println("Overloaded main");
}
⚠️ JVM always calls:
public static void main(String[] args)
Compile-Time Polymorphism Explained
- Method call resolution happens at compile time
- Based on reference type and arguments
- Faster than runtime polymorphism
Common Beginner Mistakes
- Changing only return type
- Confusing overloading with overriding
- Creating ambiguous overloads
- Misunderstanding type promotion
- Overusing overloading unnecessarily
Interview-Ready Answers
Short Answer
Method overloading allows multiple methods with the same name but different parameter lists.
Detailed Answer
In Java, method overloading is a compile-time polymorphism feature where methods share the same name but differ in number, type, or order of parameters. The return type alone cannot differentiate overloaded methods.
Method Overloading Examples (With Outputs)
1. Basic Method Overloading (Different Parameter Count)
class Demo {
static void add(int a, int b) {
System.out.println(a + b);
}
static void add(int a, int b, int c) {
System.out.println(a + b + c);
}
public static void main(String[] args) {
add(2, 3);
add(2, 3, 4);
}
}
Explanation
- Same method name
- Different number of parameters
Output
5
9
2. Overloading with Different Data Types
class Demo {
static void show(int a) {
System.out.println("int");
}
static void show(String a) {
System.out.println("String");
}
public static void main(String[] args) {
show(10);
show("Java");
}
}
Explanation
Parameter type decides method.
Output
int
String
3. Overloading with Different Parameter Order
class Demo {
static void test(int a, String b) {
System.out.println("int, String");
}
static void test(String b, int a) {
System.out.println("String, int");
}
public static void main(String[] args) {
test(10, "Java");
test("Java", 10);
}
}
Explanation
Order matters.
Output
int, String
String, int
4. Overloading with Same Parameters (❌ Not Allowed)
class Demo {
// static void show(int a) {}
// static int show(int a) {} // Compile-time error
}
Explanation
Return type alone cannot overload a method.
5. Automatic Type Promotion in Overloading
class Demo {
static void show(long a) {
System.out.println("long");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
int promoted to long.
Output
long
6. Type Promotion Preference Order
class Demo {
static void show(long a) {
System.out.println("long");
}
static void show(double a) {
System.out.println("double");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
int → long preferred over double.
Output
long
7. Primitive vs Wrapper Overloading
class Demo {
static void show(int a) {
System.out.println("int");
}
static void show(Integer a) {
System.out.println("Integer");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
Primitive preferred over wrapper.
Output
int
8. Autoboxing in Overloading
class Demo {
static void show(Integer a) {
System.out.println("Integer");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
int → Integer (autoboxing).
Output
Integer
9. Overloading with null Argument (Ambiguity)
class Demo {
static void show(String s) {
System.out.println("String");
}
static void show(Integer i) {
System.out.println("Integer");
}
public static void main(String[] args) {
// show(null); // Compile-time error (ambiguous)
}
}
Explanation
- null matches both reference types
- Causes ambiguity
10. Resolving null Ambiguity
class Demo {
static void show(String s) {
System.out.println("String");
}
static void show(Integer i) {
System.out.println("Integer");
}
public static void main(String[] args) {
show((String) null);
}
}
Explanation
Explicit casting resolves ambiguity.
Output
String
11. Overloading with Varargs
class Demo {
static void show(int a) {
System.out.println("int");
}
static void show(int... a) {
System.out.println("varargs");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
Exact match preferred over varargs.
Output
int
12. Only Varargs Method
class Demo {
static void show(int... a) {
System.out.println(a.length);
}
public static void main(String[] args) {
show(1, 2, 3);
}
}
Explanation
Varargs acts like array.
Output
3
13. Overloading with Arrays vs Varargs
class Demo {
static void show(int[] a) {
System.out.println("array");
}
static void show(int... a) {
System.out.println("varargs");
}
public static void main(String[] args) {
show(new int[]{1, 2});
}
}
Explanation
Array is more specific.
Output
array
14. Overloading Static Methods
class Demo {
static void run() {
System.out.println("no args");
}
static void run(int a) {
System.out.println("int arg");
}
public static void main(String[] args) {
run();
run(5);
}
}
Explanation
Static methods can be overloaded.
Output
no args
int arg
15. Overloading Non-Static Methods
class Demo {
void test() {
System.out.println("no args");
}
void test(String s) {
System.out.println(s);
}
public static void main(String[] args) {
Demo d = new Demo();
d.test();
d.test("Java");
}
}
Explanation
Object-level overloading.
Output
no args
Java
16. Overloading Constructors
class Demo {
Demo() {
System.out.println("default");
}
Demo(int a) {
System.out.println("parameterized");
}
public static void main(String[] args) {
new Demo();
new Demo(10);
}
}
Explanation
Constructors can be overloaded.
Output
default
parameterized
17. Overloading vs Overriding (Key Difference)
class A {
void show(int a) {}
}
class B extends A {
// void show(String s) {} // Overloading, not overriding
}
Explanation
- Overloading → compile-time
- Overriding → runtime
18. Method Overloading Resolution Priority
class Demo {
static void show(int a) {
System.out.println("int");
}
static void show(long a) {
System.out.println("long");
}
static void show(Integer a) {
System.out.println("Integer");
}
public static void main(String[] args) {
show(10);
}
}
Explanation
Priority: Exact match → Widening → Boxing.
Output
int
19. Invalid Overloading with Access Modifier Change
class Demo {
// public void test(int a) {}
// private void test(int a) {} // Not overloading
}
Explanation
Access modifier change alone is invalid.
20. Interview Summary – Method Overloading
class Demo {
static void show(int a) {
System.out.println("int");
}
static void show(long a) {
System.out.println("long");
}
public static void main(String[] args) {
show(5);
}
}
Explanation
- Compile-time binding
- Most specific match wins
Output
int
Key Takeaway
Method overloading provides flexibility and cleaner APIs, but it must be used carefully to avoid ambiguity and maintain readability.