常用高阶函数了解及使用

1. .let{} 函数

源码   inline  扩展函数  T 是输入类型或者调用对象的类型  R 是返回类型
       let函数底层的inline扩展函数+lambda结构
@kotlin.internal.InlineOnly
public inline fun <T, R> T.let(block: (T) -> R): R {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    return block(this)
}


函数内使用该对象 都用it指代  返回值为函数块的最后一行或指定return表达式。

1 .let 的第一种用途  
object.let {
  it.xxx() //在函数体没使用it 来替代 object 对象去访问其共有的属性和方法
}   
或者
?.let  第二种用途 进object的不为空操作   为空 则不进行函数内的后续操作
object?.let{  // 表示 object 不为空的后续执行
it.xxx()
}


2.适用场景
 对为空的对象进行判空处理

2. with()函数


源码   with函数是接收了两个参数,分别为T类型的对象receiver和一个lambda函数块
@kotlin.internal.InlineOnly
public inline fun <T, R> with(receiver: T, block: T.() -> R): R {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    return receiver.block()
}

1. 使用方式   它是将某对象作为函数的参数,在函数块内可以通过 this 指代该对象。
返回值为函数块的最后一行或指定return表达式。
with(object){
//todosometing  直接访问该对象的属性和方法 无需object.xxx   直接xxx
}

2.适用范围
 调用同一个类的多个方法时,可以省去类名重复,直接调用类的方法即可,
例如经常用于Android中RecyclerView中onBinderViewHolder中,数据model的属性设置到控件上

3. .run{}函数

源码  run函数实际上可以说是let和with两个函数的结合体,run函数只接收一个lambda函数为参数,
以闭包形式返回,返回值为最后一行的值或者指定的return的表达式。
@kotlin.internal.InlineOnly
public inline fun <R> run(block: () -> R): R {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    return block()
}
1. 使用方式 
 object.run{  当with 使用 
}
或者
object?.run{// with 和?.let 的 结合使用
}

2.适用场景
适用于let,with函数任何场景。因为run函数是let,with两个函数结合体,
准确来说它弥补了let函数在函数体内必须使用it参数替代对象
,在run函数中可以像with函数一样可以省略,
直接访问实例的公有属性和方法,另一方面它弥补了with函数传入对象判空问题,
在run函数中可以像let函数一样做判空处理

4 .apply{}函数

源码  apply函数的返回的是传入对象的本身。
@kotlin.internal.InlineOnly
public inline fun <T> T.apply(block: T.() -> Unit): T {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    block()
    return this
}
1.使用方式
val object=object.apply{

}
2.适用场景
一般用于一个对象实例初始化的时候,需要对对象中的属性进行赋值。
或者动态inflate出一个XML的View的时候需要给View绑定数据也会用到,这种情景非常常见。
特别是在我们开发中会有一些数据model向View model转化实例化的过程中需要用到。

5 .also{}函数


源码   also函数的结构实际上和let很像唯一的区别就是返回值的不一样,
let是以闭包的形式返回,返回函数体内最后一行的值,
如果最后一行为空就返回一个Unit类型的默认值。而also函数返回的则是传入对象的本身
@kotlin.internal.InlineOnly
@SinceKotlin("1.1")
public inline fun <T> T.also(block: (T) -> Unit): T {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    block(this)
    return this
}

1.使用方式
object.also{

}

2.适用场景
适用于let函数的任何场景,also函数和let很像,
只是唯一的不同点就是let函数最后的返回值是最后一行的返回值而also函数的返回值是返回当前的这个对象。
一般可用于多个扩展函数链式调用

6. 总结

函数名 函数体内对象使用 返回值 适用场景
let it.xxx 最后一行的类型
或者unit 类型返回
处理不为null 的数据
with this.xxx或者
xxx 的方法或属性
最后一行的类型
或者unit 类型返回
调用同一个类的多个方法时,可以省去类名重复,
直接调用类的方法即可,例如经常用于Android
中RecyclerView中onBinderViewHolder中,数
据model的属性设置到控件上
run this.xxx或者
xxx 的方法或属性
最后一行的类型
或者unit 类型返回
适用于let,with函数任何场景。因为run函数是let,
with两个函数结合体,准确来说它弥补了let函数
在函数体内必须使用it参数替代对象,在run函数
中可以像with函数一样可以省略,直接访问实例
的公有属性和方法,另一方面它弥补了with函数
传入对象判空问题,在run函数中可以像let函数
一样做判空处理
apply this.xxx或者
xxx 的方法或属性
使用的当前对象 1. 适用于run函数的任何场景,一般用于初始化
一个对象实例的时候,操作对象属性,并最终返
回这个对象。2.动态inflate出一个XML的View的
时候需要给View绑定数据也会用到.一般可用于
多个扩展函数链式调用 数据model多层级包裹
判空处理的问题
also it.xxx的方法或属性 使用的当前对象 适用于let函数的任何场景,一般可用于多个扩展
函数链式调用
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容