对 Lambda 的理解我觉得要会两点,1.看得的 lambda 代码,2.会基本的 lambda 表达式。掌握这两点至少在平时的项目开发上问题就不大了。
lambda 是什么
本质上就是可以传递给其他函数的一段代码。以一个例子来说明,比如 Android 里的 setOnClickListener() 方法,入参需要一个实现 OnClickListener 接口的实例对象,通常在 Java 里我们会实现一个匿名内部类,到了函数式编程,这个匿名内部类就变成了函数实现,再到 lambda 就简化成了一段代码。
lambda 的用途
- 替换只有一个方法的匿名对象(就如 OnClickListener 那样)
- 为集合提供一系列的标准库函数
lambda 表达式
表达式的语法如下,
//始终是在{}大括号里
{实参列举 -> 函数体}
//实参列举就是指要将实参一一列出,比如
{a: Int, b: Int -> a + b}
//上面就表示 a + b 的操作
//重点:为了更加简化,我们可以省略a, b 的 Int 类型,但在实际项目中,这个要依赖于编译器推导,如果推导失败,还是要加上参数类型的。
//重点:如果实参只有一个,默认情况下 lambda 还提供了 it 命名,可以用 it 代替我们的实参名称
//把这样的一个 lambda 表达式作为函数入参传递给其他函数时
//重点:1.如果 lambda 作为最后一个入参,则可以从()里拿出来放在后面
sum(a, {x, y -> x + y})
//可以等价于
sum(a){x, y -> x + y}
//重点:2.如果 lambda 作为仅有的入参,则可以省略()
display({x, y -> x + y})
//可以等价于
display{x, y -> x + y}
总的来说,lambda 可以极大的简化我们的代码,但也由此增加了代码难理解,不好阅读的程度,所以实际项目中要做到适度。
lambda 捕捉
谈 lambda 捕捉其实是从 Java 匿名内部类引用外部方法其他入参或者局部变量时需要转为 final 说起。用 lambda 代替匿名内部类是没有 final 这样的限制的,它可以任意引用,修改。
引用书中原话 当你捕捉 final 变量时,它的值和使用这个值的 lambda 代码一起存储,而对非 final 变量来说,它的值被封装在一个特殊的包装器中,这样你就可以改变这个值,而对这个包装器的引用会和 lambda 代码一起存储,其实说白了,最终的实现原来和 Java 应该是没有差别的,只不过 lambda 为我们做了简化。
lambda 成员引用
同 lambda 表达式一样,lambda 成员引用也有语法,
类名::成员
//这里的成员应该是成员变量或者成员函数
//什么场景会用到呢?我理解的是,当根据上下文没法推导出 it 变量时可以用成员引用来调用
//就目前使用和看到的代码而言还没有用到过
总之我们知道了 Lambda 是什么,有什么用,怎么用。在实际项目中基本的 lambda 写法也应该能看懂的一二了。要想灵活运用,还得靠多写多练。
参考内容
「Kotlin 实战」
网友评论