Java 已解析不明确的重载方法调用
当我调用时,Java 已解析不明确的重载方法调用,java,overloading,Java,Overloading,当我调用时,调用('a')它输出“char”,这很好,因为char原语类型将优先于将其装箱到Character static void call(char i){ System.out.println("char"); } static void call(Character i){ System.out.println("Character"); } 如何调用调用('a','a')不明确 static void call(char i, Character j){
调用('a')代码>它输出“char”,这很好,因为char原语类型将优先于将其装箱到Character
static void call(char i){
System.out.println("char");
}
static void call(Character i){
System.out.println("Character");
}
如何调用调用('a','a')代码>不明确
static void call(char i, Character j){
System.out.println("char");
}
static void call(Character i, Character j){
System.out.println("Character");
}
我想的是,对于第二个参数,编译器必须进行装箱,对于第一个参数,完美匹配是char基元类型,所以调用call('a','a')代码>可以解析为调用(字符i,字符j)
方法
显然我理解错了,请有人解释一下
解释此类示例的某些链接将很有帮助
如何调用调用('a','a')代码>不明确
static void call(char i, Character j){
System.out.println("char");
}
static void call(Character i, Character j){
System.out.println("Character");
}
因为为了使(char i,Character j)
重载适用,围绕装箱的规则将发挥作用-在这一点上,两个调用都适用。这是确定方法签名的第二阶段:
第一阶段(§15.12.2.2)执行重载解析,不允许装箱或拆箱转换,也不允许使用变量arity方法调用。如果在此阶段没有找到适用的方法,则处理继续到第二阶段
第二阶段(§15.12.2.3)在允许装箱和拆箱的同时执行重载解析,但仍然禁止使用变量arity方法调用。如果在此阶段没有找到适用的方法,则处理继续到第三阶段
因此,在第2阶段,这两种方法都是适用的,但是确定最具体的方法()的规则不会使两个调用中的任何一个都比另一个更具体。这不是一个“未装箱比装箱更具体”的问题,而是一个在“我可以用装箱来解决这个问题”之前的“我可以不用装箱来解决这个问题”的问题。答案在:
对于使用char
和Character
调用方法的第一次调用,编译器只需要第一个阶段就可以知道调用哪个方法。在第一阶段,它不会混合装箱和基本类型:
第一阶段(§15.12.2.2)执行重载解析,不允许装箱或拆箱转换,也不允许使用变量arity方法调用。如果在此阶段没有找到适用的方法,则处理继续到第二阶段
但是,在使用两个参数(char
和Character
,以及Character
和Character
)的调用中,编译器需要进入第二个阶段,尝试区分它们,在特定点,两种方法都有效:
第二阶段(§15.12.2.3)在允许装箱和拆箱的同时执行重载解析,但仍然禁止使用变量arity方法调用
编译器不会进入第三阶段,因为这两个阶段都适用于第二阶段。“第二阶段(§15.12.2.3)在允许装箱和拆箱的同时执行重载解析,但仍然禁止使用变量arity方法调用。如果在此阶段未找到适用的方法,则处理将继续到第三阶段。”如果我理解正确,在3条JLS规则中,通过在不考虑装箱和拆箱的情况下应用第一条规则,调用(字符i,字符j)不明确,因为第一个参数可以解析,但第二个参数需要装箱,它超出了第一条规则的范围,控制传递到第二条规则,在第二条规则中考虑装箱和拆箱,因此在这种情况下,两个调用(字符i,字符j)和调用(字符i,字符j)是适用的,因为它无法解决这就是为什么它给出编译错误?请确认我的理解是否正确。谢谢。我的问题是,在第二条规则中,它是否只是检查所有的方法组合,并且调用映射到许多方法,这就是它给出错误的原因?我在想,在第二条规则中,它可能会检查调用的第一个参数(char I,Character j)是否完全匹配,第二个参数调用是否通过装箱来解决,@Jayesh:是的,它将进入第二阶段,在这一点上,两种方法都不比另一种方法更具体。请注意,“更具体”并没有查看实际的调用-要么一个方法比另一个更具体,要么不是。在这种情况下,两者都不比另一个更具体。