Kotlin standard library commonly spread function summary

Kotlin standard library has some very useful extension functions.

  • run
/**
 * Calls the specified function [block] with `this` value as its receiver and returns its result.
 */
@kotlin.internal.InlineOnly
public inline fun <T, R> T.run(block: T.() -> R): R {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    return block()
}

run is the generic spread function of any type T, a return run is performed for the R type of extension function block, the final result of the extension function returns.

In the run function, we have a separate scope, to redefine a new variable, and its scope exists only in the run function.

fun testPayFoo() {
    val nickName = "Perfect"

    run {
        val nickName = "PAYZY"
        println(nickName)
    }

    println(nickName)
}

fun main() {
    testPayFoo()
}

PAYZY
Perfect

And it returns the last object in the range.

example:

data class StuA(val name: String)

fun testPayFoo2() {
    val run = run {
        println("test return")
        StuA("PAYZY")
    }
    println(run)
}

fun main() {
    testPayFoo2()
}

test return
StuA(name=PAYZY)

 

  • let
/**
 * Calls the specified function [block] with `this` value as its argument and returns its result.
 */
@kotlin.internal.InlineOnly
public inline fun <T, R> T.let(block: (T) -> R): R {
    contract {
        callsInPlace(block, InvocationKind.EXACTLY_ONCE)
    }
    return block(this)
}

and let apply similar, the only difference is the return value: apply returns the original object, and let the return value inside the closure. let also limits the scope of the variable.

data class Student(val age: Int)
class PayKot {
    val stu: Student? = Student(2)
    fun dealStu() {
        val result = stu?.let {
            println(it.age)
            it.age
        }
        println("result:$result")
    }
}


fun main() {
    PayKot().dealStu()
}

2
result:2

 

 

  • also

Content Kotlin1.1 version is also newly added, it is like an enhanced version of let and apply functions.

/**
 * Calls the specified function [block] with `this` value as its argument and returns `this` value.
 */
@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
}

And apply a consistent, its return value is a function of the receiver.

data class PayStudent(val age: Int)
class PayZKot {
    val student: PayStudent? = PayStudent(666)
    var age = 0
    fun dealStu() {
        val result = student?.also { stu ->
            this.age += stu.age
            println(this.age)
            println(stu.age)
            this.age
        }
        println("result:$result")
    }
}

fun main() {
    PayZKot().dealStu()
}

666
666
result:PayStudent(age=666)

In the above code, it is implicitly specified as stu, assuming that student? Not empty, will return student, and the total age of this.age increased.

The main note: If you use apply, because it is an extension of the internal function, this will point to the stu rather than PayZKot, at this time can not be invoked to age under PayKot.

 

  • takeIf

If you just want to empty sentence, also added the condition, then let it inadequate. Then you can use takeIf.

/**
 * Returns `this` value if it satisfies the given [predicate] or `null`, if it doesn't.
 */
@kotlin.internal.InlineOnly
@SinceKotlin("1.1")
public inline fun <T> T.takeIf(predicate: (T) -> Boolean): T? {
    contract {
        callsInPlace(predicate, InvocationKind.EXACTLY_ONCE)
    }
    return if (predicate(this)) this else null
}

This function is also in Kotlin1.1 newly added. When the receiver satisfy certain conditions will be performed.

example:

class PayTestTakeIf {
    val stuA: PayStudent2? = PayStudent2(55)
    val stuB: PayStudent2? = PayStudent2(5)

    fun dealStu() {
        val let = stuA?.takeIf { it.age > 10 }?.let {
            println(it.age)
            it.age
        }
        println("let:$let")

        val takeIf = stuB?.takeIf { it.age > 10 }
        println(takeIf)
    }
}

fun main() {
    PayTestTakeIf().dealStu()
}

55
let:55
null

 

 Reference Kotlin core programming

 

 

 

 

 

 

 

 

He published 182 original articles · won praise 179 · views 120 000 +

Guess you like

Origin blog.csdn.net/zhangying1994/article/details/104875942