public class Yikes {
public static void go(Long n) {
System.out.print("Long ");
}
public static void go(Short n) {
System.out.print("Short ");
}
public static void go(int n) {
System.out.print("int ");
}
public static void main(String[] args) {
short y = 6;
long z = 7;
go(y);
go(z);
}
}
该程序提供输出
int Long
我认为输出是
short Long
这是什么原因?
答案 0 :(得分:17)
overload resolution section in the JLS解释了原因:
- 第一阶段(§15.12.2.2)执行重载解析,不允许装箱或拆箱转换,或使用变量arity方法调用。如果在此阶段没有找到适用的方法,则处理继续到第二阶段。
醇>这保证了在Java SE 5.0之前在Java编程语言中有效的任何调用都不会被认为是引入变量arity方法,隐式装箱和/或取消装箱的结果。但是,变量arity方法(第8.4.1节)的声明可以更改为给定方法方法调用表达式选择的方法,因为变量arity方法在第一阶段被视为固定arity方法。例如,在已声明
m(Object...)
的类中声明m(Object)
会导致某些调用表达式(例如m(Object)
)不再选择m(null))
,因为m(Object[])
更具体。
- 第二阶段(§15.12.2.3)执行重载解析,同时允许装箱和拆箱,但仍然排除使用变量arity方法调用。如果在此阶段没有找到适用的方法,则处理继续到第三阶段。
醇>
在第一阶段,编译器在其分辨率中不包含方法go(Short n)
。相反,它认为go(int n)
是一种适用的方法。此方法适用,因为short
正在加宽转换为int
。
答案 1 :(得分:5)
编译器更愿意将short
转换为int
,而不是将其格式化为Short
对象。
答案 2 :(得分:0)
试试这个:
而不是
public static void go(Short n) {
System.out.print("Short ");
}
试
public static void go(short n) {
System.out.print("Short ");
}