编译器如何确保以下语句的等效lambda
BinaryOperator<String> concatOperator = String::concat;
是
BinaryOperator<String> concatOperator = (resultString, inputString) -> resultString.concat(inputString);
而不是
BinaryOperator<String> concatOperator = (resultString, inputString) -> inputString.concat(resultString);
这种行为在 JLS 中有很好的记录
15.13.3. 方法引用的运行时评估
如果编译时声明是实例方法,则目标引用是调用方法的第一个形式参数。否则,没有目标引用。
如果编译时声明是实例方法,则方法调用表达式的参数(如果有(是调用方法的第二个和后续形式参数。否则,方法调用表达式的参数是调用方法的形式参数。
这似乎是合理和直观的。如果采用 arityn
(n > 2
( 的方法,很明显,目标引用应该是第一个参数,而不是最后一个,也不是中间的参数。
使用方法引用的代码行在方法引用类型下分类为 -
对特定类型的任意对象的实例方法的引用
其中,第一个 lambda 参数被推断为类型String
的对象,在该对象上调用名为concat
的方法,参数值等效于第二个 lambda 参数。在上述情况下为:
BinaryOperator<String> concatOperator = (result, input) -> result.concat(input);