我们可以用@FunctionalInterface注解来标注一个函数式接口。编译器不使用这个注解,不过有了它可以更明确的标识这个接口的类型。不止如此,如果我们用这个注解标注了一个接口,编译器会强制校验它是否符合函数式接口的规则。
如果一个方法接收函数式接口作为参数,我们可以传递的参数包括:
匿名内部类,最古老的方式
lambda表达式,就像我们在map方法里那样
方法或者构造器的引用(后面我们会讲到)
如果方法的参数是函数式接口的话,编译器会很乐意接受lambda表达式或者方法引用作为参数。
如果我们把一个lambda表达式传递给一个方法,编译器会先把这个表达式转化成对应的函数式接口的一个实例。这个转化可不止是生成一个内部类而已。同步生成的这个实例的方法对应于参数的函数式接口的抽象方法。比如,map方法接收函数式接口Function作为参数。在调用map方法时,java编译器会同步生成它,就像下图所示的一样。
lambda表达式的参数必须和接口的抽象方法的参数匹配。这个生成的方法将返回lambda表达式的结果。如果返回类型不直接匹配抽象方法的话,这个方法会把返回值转化成合适的类型。
我们已经大概了解了下lambda表达式是如何传递给方法的。我们先来快速回顾一下刚讲的内容,然后开始我们lambda表达式的探索之旅。
总结
这是Java一个全新的领域。通过高阶函数,我们现在可以写出优雅流利的函数式风格的代码了。这样写出的代码,简洁易懂,错误少,利于维护和并行化。Java编译器发挥了它的魔力,在接收函数式接口参数的地方,我们可以传入lambda表达式或者方法引用。
我们现在可以进入lambda表达式以及为之改造的JDK库的世界来感觉它们的乐趣了。在下一章中,我们将从编程里面最常见的集合操作开始,发挥lambda表达式的威力。
译注:终于搞完无聊的第一章了。下一章开始会有更多实际的例子了。
未完待续,后续文章请继续关注deepinmind。
原创文章转载请注明出处:http://it.deepinmind.com