503 字
3 分钟
Kotlin内联函数
2023-07-20

前言#

TIP

以下的文章均基于以下示例代码

class Calculator {
var a: Int = 0
var b: Int = 0
fun add() = a + b
fun multiply() = a * b
}
fun main() {
val calculator = Calculator()
doCalculation(calculator)
}

run 函数#

run 的标准函数形式#

fun doCalculation(calculator: Calculator) {
val result = run {
calculator.a = 1
calculator.b = 2
calculator.add()
}
println(result)
}

run 的标准函数形式能够在 Lambda 中执行操作,并返回一个结果,此结果即为 Lambda 中最后一行表达式

run 的扩展函数形式#

fun doCalculation(calculator: Calculator) {
val result = calculator.run {
a = 1
b = 2
add()
}
println(result)
}

run 此时被定义为接收者的扩展函数,它能够接收一个带有接收者(reciver)的 Lambda。在reciver中,能够访问调用者的上下文

with 函数#

在 with 内处理结果#

fun doCalculation(calculator: Calculator) {
val resultOne = with(calculator) {
a = 1
b = 2
add()
}
println(resultOne)
}

with 中也拥有reciver(接收者)。此时 with 的最后一个表达式即为 with 的返回值。若要让代码返回到 with,而不是直接 return 整个函数,可以使用return@with

在 with 外处理结果#

fun doCalculation(calculator: Calculator) {
with(calculator) {
a = 3
b = 4
}
val resultTwo = calculator.add()
println(resultTwo)
}

在这一种处理方式中,with 仅用于对对象统一的操作,而不直接返回值。

apply 函数#

fun doCalculation(calculator: Calculator) {
val result = calculator.apply {
a = 1
b = 2
}.add()
println(result)
}

在 apply 的 Lambda 中,同样存在着接收者(reciver)。 在 apply 函数中,Lambda 在调用过后将会返回函数自身,因此不会打断函数后面的调用链。

let 函数#

fun main(){
val values = listOf("aaaa", "bbbbb", null, "ccccccc", "ddddd", null)
for (str in values) {
str?.let { println(it) }
}
}

let 对应着 run,为 run 不含有receiver的版本。通过使用?配合 let,能够确保空安全。

also#

fun doCalculation(calculator: Calculator) {
val result = calculator.apply {
a = 1
b = 2
}.add().also { println(it) }.times(5) // .times()实际上就是 * 的重载函数
println(result)
}

also 对应着 apply,为 apply 不含有receiver的版本。also 同样返回调用者本身,不会打断调用链

Kotlin内联函数
https://www.persicif.xyz/posts/inline-functions/
作者
HyperCherry
发布于
2023-07-20
许可协议
CC BY-NC-SA 4.0
评论