Java 可变参数方法重载编译器错误 - 歧义?

Java varargs method overloading compiler error - ambiguity?

所以,今天我一直在测试 Java 的重载技术,但遇到了我无法解释的歧义。基本上,当存在带有原语及其相应包装器的可变参数方法时,编译器会抱怨并且无法决定选择哪一个,我不明白为什么?人类很容易决定而不是编译器?

这是适用于非可变参数的片段:

public static void main(String[] args)
{
    int a = 14;
    Integer b = new Integer(14);
    stuff(a);
    stuff(b);
}

static void stuff(Integer arg) { System.out.println("Integer"); }
static void stuff(int arg) { System.out.println("int"); }

来了 vararg,它像婴儿一样抱怨和哭泣:

public static void main(String[] args)
{
    int a = 14;
    Integer b = new Integer(14);
    stuff(a); // Doesn't compile (ambiguity)
    stuff(b); // Doesn't compile (ambiguity)
}

static void stuff(int... arg) { System.out.println("varargs int"); }
static void stuff(Integer... arg) { System.out.println("varargs Integer"); }

问题是:

java 正在幕后进行桥接方法(您需要验证是否需要深入信息)

重要的是,vargargs 也意味着 你不能传递任何参数,所以:

static void stuff(int... arg)   

static void stuff(Integer... arg) 

两者都可以在不带参数的情况下被调用...所以这将在 JVM 应该调用什么方法方面产生一些冲突

考虑以下对 stuff() 的两个假设调用:

int a = 14;
Integer b = new Integer(14);

stuff(a, b);
stuff(b, a);

编译器怎么知道应该在这里调用哪个方法?由于自动装箱规则,任一调用都可以引用任一重载方法。

更新:

我的回答在逻辑上是正确的,或者至少是在正确的轨道上,但是更正式的回答我们可以参考这个SO问题:

Why ambiguous error when using varargs overloading with primitive type and wrapper class?

这两个可变参数方法是在松散调用上下文中调用的。因此,编译器将尝试通过 JLS 15.12.2.5 Choosing the Most Specific Method 找到更具体的方法。但是,由于 intInteger 都不是彼此的子类型,因此编译器会抛出错误。