Kotlin常用标准库的扩展函数

with

with 是将某个对象作为函数的参数,在函数块内可以通过 this 指代该对象。

//使用 with 之后,在 with 函数块内可以省略"content."
class AppPublisherAdapter : BaseAdapter<BoundAppInfoResponse.AppInfo>() {

    override fun getLayoutId(viewType: Int): Int = R.layout.cell_app_publisher

    override fun onBindViewHolderImpl(holder: BaseViewHolder, position: Int, content: BoundAppInfoResponse.AppInfo) {

        with(content) {
            holder.itemView.tv_game_name.text = name

            if (is_bound) {
                holder.itemView.tv_bound_user_name.text = bound_user_name
                holder.itemView.tv_bound_user_name.setTextColor(context.color(R.color.color_bound_user_name))
            } else {
                holder.itemView.tv_bound_user_name.text = context.string(R.string.bind_on_account)
                holder.itemView.tv_bound_user_name.setTextColor(context.color(R.color.color_bind_on_account))
            }
            holder.itemView.iv_game_icon.load(logo_url)
        }
    }
}

apply

apply 函数是指在函数块内可以通过 this 指代该对象,返回值为该对象自己。

	@JvmStatic
    fun main(args: Array<String>) {
        val result ="Hello".apply {
            println(this+" World")

            this+" World" // apply 会返回该对象自己,所以 result 的值依然是“Hello”
        }

        println(result)
    }

run

run 函数类似于 apply 函数,但是 run 函数返回的是最后一行的值。

	@JvmStatic
    fun main(args: Array<String>) {
        val result ="Hello".run {
            println(this+" World")

            this + " World" // run 返回的是最后一行的值 Hello World
        }

        println(result)
    }

let

let 函数把当前对象作为闭包的 it 参数,返回值是函数里面最后一行,或者指定 return。它看起来有点类似于 run 函数。

let 函数跟 run 函数的区别是:let 函数在函数内可以通过 it 指代该对象。

//可以在 obj 不为 null 的情况下执行 let 函数块的代码,从而避免了空指针异常的出现。
obj?.let {
   ....
}

also

also 是 Kotlin 1.1 新增的函数,类似于 apply 的功能。跟 apply 不同的是,also 在函数块内可以通过 it 指代该对象,返回值为该对象自己。

	@JvmStatic
    fun main(args: Array<String>) {
        val result ="Hello".also {
            println(it + " World")

            it + " World"
        }

        println(result) //Hello
    }

例举完 Kotlin 标准库常用的几个扩展函数之后,我们会发现它们都是高阶函数,而且还都使用了inline。
在这里插入图片描述

inline

Kotlin 的内联函数是使用inline修饰的函数,从编译器角度将函数的函数体复制到调用处实现内联。
本质上,内联函数的使用是空间换取时间的过程。

示例1

在 main 函数中,分别使用内联函数和非内联函数打印一段文字。

fun nonInlined(block: () -> Unit) { // 不用内联的函数
    block()
}

inline fun inlined(block: () -> Unit) { // 使用内联的函数
    block()
}

fun main(args: Array<String>) {
    nonInlined {
        println("do something with nonInlined")
    }

    inlined {
        println("do something with inlined")
    }
}

其中 nonInlined 需要创建 Function0 对象。而使用了内联的 inlined 函数,它不用再创建 Function0 对象,直接被复制到被调用处。

示例2

对 Closeable 类进行扩展,让它支持 Java 的try-with-resources特性。其实,在 Kotlin 1.2 后已经在 Closeable.kt 中增加了扩展函数 use(),跟下面的代码类似:

inline fun <T : Closeable?, R> T.use(block: (T) -> R): R {
    var closed = false
    try {
        return block(this)
    } catch (e: Exception) {
        closed = true
        try {
            this?.close()
        } catch (closeException: Exception) {
        }
        throw e
    } finally {
        if (!closed) {
            this?.close()
        }
    }
}

使用这个 use() 方法:

 	val sourceString = "write something to test.txt"
    val sourceByte = sourceString.toByteArray()
    val file = File("test.txt")
    if (!file.exists()) {
        file.createNewFile()
    }
    FileOutputStream(file).use { // 使用了扩展函数 use 之后,就无需再主动关闭FileOutputStream
        it.write(sourceByte)
    }

Kotlin 的代码节省了try…catch…finally语句,并自动关闭了文件输出流。

小结一下内联函数的特性:

  • 内联函数中有函数类型的参数,那么该函数类型的参数默认也是内联的。除非,显示使用noinline进行修饰,那样该函数类型就不再是内联的。
  • 内联函数的优点是效率高、运行速度快。
  • 内联函数的缺点是编译器会生成比较多的代码,所以内联函数不要乱用。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值