Java 重载解析 lambda

在Java中可以重载方法,造成多个方法有相同的方法名,但签名确不一样。这在推断参数类型时会带来问题,因为系统可能会推断出多种类型。这时,javac会挑出最具体的类型。如下文中的方法调用在选择定义的重载方法时,输出String,而不是Object

overloadedMethod("abc");

对应的接口定义

 private void overloadedMethod(Object o) {
        System.out.println("Object");
 }

private void overloadMethod(String s) {
        System.out.println("String");
}

BinaryOperator是一种特殊的BiFunction类型,参数的类型和返回值的类型相同。比如,两个整数相加就是一个BinaryOperator。Lambda表达式的类型就是对应的函数接口类型,因此,将Lambda表达式作为参数传递时,情况也依然如此。操作时可以重载一个方法,分别接受BinaryOperator和该接口的一个子类作为参数。调用这些方法时,Java推导出的Lambda表达式的类型正是最具体的函数接口的类型。

@Slf4j
public class lambdaTest {

    private interface IntegerBiFunction extends BinaryOperator<Integer> {
    }

    private interface NanoIntegerBiFunction extends IntegerBiFunction {

    }

    private void overloadedMethod(BinaryOperator<Integer> lambda) {
        System.out.println("BinaryOperator");
    }

    private void overloadedMethod(NanoIntegerBiFunction lambda) {
        System.out.println("NanoIntegerBiFunction");
    }

    private void overloadedMethod(IntegerBiFunction lambda) {
        System.out.println("IntegerBinaryOperator");
    }

   

    @Test
    public void overloadTest() {
        overloadedMethod((x, y) -> x + y);
    }
}

输出结果为
NanoIntegerBiFunction

//重载方法导致的编译错误

    private interface IntPredicate {
        public boolean test(int value);
    }

    private void overloadMethod2(Predicate<Integer> predicate) {
        System.out.println("Predicate");
    }

    private void overloadMethod2(IntPredicate predicate) {
        System.out.println("IntPredicate");
    }

    @Test
    public void overloadErrTest() {
        overloadMethod2(((Predicate<Integer>) (x) -> x > 10));
        overloadMethod2((IntPredicate) (x) -> x > 10);
        //error code 
        overloadMethod2((x) -> x > 10);
		/*        
		Ambiguous method call. Both
		overloadMethod2 (Predicate<Integer>) in lambdaTest and
		overloadMethod2 (IntPredicate)	in lambdaTest match
		*/        
    }

传入overloadedMethod方法的Lambda表达式和两个函数接口Predicate、IntPredicate在类型上都是匹配的。在这段代码块中,两种情况都定义了相应的重载方法,这时,javac就无法编译,在错误报告中显示Lambda表达式被模糊调用。IntPredicate没有继承Predicate,因此编译器无法推断出哪个类型更具体。

将Lambda表达式强制转换为IntPredicate或Predicate类型可以解决这个问题,至于转换为哪种类型则取决于要调用哪个函数接口

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值