Generic type T

First let’s take a look at the source code for Apply

 

fun T.apply(block: T.() -> Unit): T { block(); return this }
Copy the code

The generic T can be null, which means that null is also assigned to the apply method

 

null.apply{
    System.out.println("null apply")
}
Copy the code

Null is not indicated by the apply method in the IDE, but can be passed in kotlin compilation

Null buried trap

Since NULL also has apply methods, block blocks are executed when applied to A nullable object (A). The global method is called if A’s method has the same name as the global method.

 

open class A {
    override fun toString(): String {
        return "this is A"
    }

    open fun methodPrint() {
        System.out.println("A print")
    }
}

class B {
    override fun toString(): String {
        return "this is B"
    }

    fun methodPrint() {
        System.out.println("B print")
    }

    fun print() {
        val a: A? = null
        System.out.println(a.apply {
            methodPrint()
            System.out.println("a.apply:" + toString())
        })
    }
}
Copy the code

The output

 

B print
a.apply:null
null
Copy the code

It’s even more subtle if B has an inheritance

 

class C : A(){
    override fun toString(): String {
        return "this is C"
    }

    fun print() {
        val a: A? = null
        System.out.println(a.apply {
            methodPrint()
            System.out.println("a.apply:" + toString())
        })
    }
}
Copy the code

The output

 

A print // The C class's methodPrint() method inherits from a. ply:null nullCopy the code

Extension of T generics

Using an extension to generics I can encapsulate a NullWork method that executes a NullBlock if an object is null and a noNullblock if the object is not.

 

inline fun <T, R> T? .nullWork(noNull: (T) -> R, isNull: () -> R): R { return this? .let {// if the block returns null, isNull() will be executed. Return noNull(it)}? : isNull() }Copy the code

conclusion

The key points of the trap are two

  1. Null objects that have apply methods cause the apply block of the null object to be executed
  2. Blcok blocks can call global methods

Author: MicroCoder links: www.jianshu.com/p/e4c026788… The copyright of the book belongs to the author. Commercial reprint please contact the author for authorization, non-commercial reprint please indicate the source.