为什么Java更喜欢调用双构造函数?

时间:2015-06-15 16:52:19

标签: java constructor

public class test {
    test(double[] a)
    {
        System.out.println("in double");
    }
    test(Object a)
    {
        System.out.println("in object");
    }
    public static void main(String args[])
    {
        new test(null);
    }
}

在上面的代码中,我传递null作为构造函数参数。由于null可以是任何东西,上面的代码编译得很好。当我运行代码时,我希望它在对象中打印,但它会在中打印 这背后的原因是什么?

注意链接的问题可能不重复,因为此问题与原始数据类型与对象相关

2 个答案:

答案 0 :(得分:21)

原因是Java将null解释为任何类型,并且在选择要调用的方法时,它将选择首先参数类型的最具体方法。由于null可以是double[]类型而double[]Object,因此编译器将选择采用double[]的方法。如果选择涉及同样可能但不相关的类型,例如double[]String,然后编译器将无法选择方法,这将导致模糊的方法调用错误。

JLS, Section 4.1,声明:

  

可以始终为空引用赋值或转换为任何引用类型(第5.2节,第5.3节,第5.5节)。

     

在实践中,程序员可以忽略null类型,只是假装null只是一个可以是任何引用类型的特殊文字。

答案 1 :(得分:9)

两个构造函数都适用,因为null可以转换为Objectdouble[] - 因此编译器需要使用重载决策来确定要调用的构造函数。

根据{{​​3}},

JLS 15.9.3使用JLS 15.12.2来确定要使用的“最具体”的构造函数签名,具体取决于哪个构造函数具有最具体的参数类型。确切的细节有点模糊(IMO),但在这种情况下,基本的经验法则是“如果你可以从T1转换为T2,而不是T2转换为T1,那么T1更具体”就足够了。

double[]是一种比Object更具体的类型,因为存在从double[]Object的隐式转换,但反之亦然。