1
public class App {
    public static void main(String[] args) {
        ConTest conTest = new ConTest(null);

    }

POJO :

public class ConTest {

    private String  a;

    private Object  b;

    public ConTest(Object b) {
        System.out.println("Object" + b);
    }

    public ConTest(String a) {
        System.out.println("String :" + a);
    }

}

When I run this piece of code it always call constructor having String argument. Why?

2
  • 3
    To call the object version, you may cast the parameter : new ConTest((Object)null); Commented Mar 17, 2016 at 8:06
  • Yes your code is working fine if I want to call object's constructor. As far as I know object is a super class for all. So it should call object constructor. Commented Mar 17, 2016 at 8:14

2 Answers 2

5

null can be passed to both constructors.

However, a String argument is more specific than an Object argument (since String is a sub-class of Object), and the method overloading resolution process prefers the method (or constructor in your case) with the more specific argument types.

As mentioned in the comments, if you want to force calling the constructor that accepts an Object, you can cast the null to Object :

ConTest conTest = new ConTest((Object)null);
Sign up to request clarification or add additional context in comments.

1 Comment

Thanks for such a great explanation.
3

The cause of this is, that there are multiple fitting methods (constructor in this case) that do fit the call. If there is more then one fitting method for a method call it allways takes the most specific one. In this case, String is more specific then Object. This can be seen in the inheritance chain. String inherits from Object

If there are two equally specific methods, then your compiler will tell you so with the error message The method method(parameter) is ambiguous for the type Class. This can be seen in this example.

public class A { 
    public static void main(String[] args) {
        // compiler complains with:
        // The method test(Object) is ambiguous for the type A
        test(null); 
    }

    static void test(Object o) {
        System.out.println("IN OBJECT");
    }

    static void test(A a) {
        System.out.println("IN A");
    }

    static void test(B b) {
        System.out.println("IN B");
    }

    class B {

    }
}

With a slight change, by letting B inherit from A the method test(B) is getting more specific, because B is more specific then A, and the compiler error message is gone.

public class A { 
    public static void main(String[] args) {
        test(null);
    }

    static void test(Object o) {
        System.out.println("IN OBJECT");
    }

    static void test(A a) {
        System.out.println("IN A");
    }

    static void test(B b) {
        System.out.println("IN B");
    }

    class B extends A{

    }
}

2 Comments

I like your answer and explanation !
Thanks for such a great explanation.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.