Kotlin之代理

xiaoxiao2021-02-28  75

package cn.zms.class2 import kotlin.properties.Delegates import kotlin.reflect.KProperty /** * 类代理:by关键字 * 属性代理:val/var <property name>: <Type> by <expression> */ interface Base{ fun print() } class BaseImpl(var x: Int) : Base{ override fun print(){ println(x) } } //类代理,通过“by”关键字,将“b”实例存储到Derived对象中,编译器会生成“Base”接口的所有方法,使用“b”的实现。 class Derived(b: Base) : Base by b //属性代理 class Example { //语法:val/var <property name>: <Type> by <expression> var p: String by DelegateTheP() } class DelegateTheP { //属性代理不需要实现任何接口,只需要提供getValue() setValue()【val属性不需要】函数 /** * thisRef p所属的Example实例 * property p实例本身的描述信息 */ operator fun getValue(thisRef: Any?, property: KProperty<*>): String { return "$thisRef, thank you for delegating '${property.name}' to me!" } operator fun setValue(thisRef: Any?, property: KProperty<*>, value: String) { println("$value has been assigned to '${property.name} in $thisRef.'") } } class UserPropertyByDelegate(val map: Map<String, Any?>) { val name: String by map val age: Int by map } class UserPropertyByDelegate2(val map: MutableMap<String, Any?>) { //var的属性代理,请使用MutableMap对象 var name: String by map var age: Int by map } fun main(args: Array<String>) { //======================1.类代理====================== val b = BaseImpl(10) Derived(b).print() //======================2.属性代理====================== val e = Example() //读取p访问DelegateTheP.getValue() println(e.p) //p的赋值会调用DelegateTheP.setValue() e.p = "123" //======================标准属性代理之:Lazy====================== /** * 默认Lazy属性是线程同步的(synchronized), * 如果不需要synchronized可以将lazy()构造函数中传入LazyThreadSafetyMode.PUBLICATION,那么多个线程可以同时赋值 * 如果可以确保属性只会在单线程中初始化,可以lazy()构造函数中传入LazyThreadSafetyMode.NONE,以节省线程开销 */ val lazyValue : String by lazy(){ //第一次访问,初始化,然后保存,相当于单例模式 println("Completed") "Hello" } //只有第一次打印才会 println(lazyValue) println(lazyValue) //======================标准属性代理之:Observable====================== //两个参数,初始化的值<no name>,修改值时的回调函数大括号中 var name: String by Delegates.observable("<no name>") { prop, old, new -> println("$old -> $new") } name = "first" name = "second" println(name) //当需要拦截修改事件,并只能判断是否允许修改,可以使用vetoable代理 var nameVeto: String by Delegates.vetoable("<no nameVeto>") { prop, old, new -> println("$old -> $new") //要有返回值,代表是否允许修改,当second赋值时才能修改 new == "second" } nameVeto = "first" println(nameVeto) nameVeto = "second" println(nameVeto) //======================标准属性代理之:Storing Properties in a Map====================== /** * 你肯定会经常使用使用Map来存储属性,常见的场景是当需要解析JSON值或其他动态的事情。 * 这时就可以使用Map对象为代理属性提供代理 */ var user = UserPropertyByDelegate(mapOf( "name" to "john", "age" to 15 )) println("${user.name} age is ${user.age}") //======================3.局部变量代理(since 1.1)====================== //局部变量同样也可以使用代理 }
转载请注明原文地址: https://www.6miu.com/read-36131.html

最新回复(0)