在Kotlin中,委托属性(Delegated Properties)是一种强大的语言特性,允许你将属性的 getter 和 setter 方法的实现委托给其他对象。这使得你能够通过委托来重用代码、将属性的行为解耦,并实现一些通用的模式。下面是一些关键概念和用法:

class Example {
var property: String by Delegate()
} class Delegate {
operator fun getValue(thisRef: Any?, property: KProperty<*>): String {
// 获取属性值的实际实现
return "Delegated value"
} operator fun setValue(thisRef: Any?, property: KProperty<*>, value: String) {
// 设置属性值的实际实现
println("Setting value to: $value")
}
}

在上面的代码中,Example类中的property属性的访问,比如,访问example.property,就会委托到Delegate.getValue; 属性值的设置example.property = "str",就会委托到

Delegae.setValue。

实际例子:

   fun saveCookie(url: String?, domain: String?, cookies: String) {
url ?: return
var spUrl: String by Preference(url, cookies)
@Suppress("UNUSED_VALUE")
spUrl = cookies
domain ?: return
var spDomain: String by Preference(domain, cookies)
@Suppress("UNUSED_VALUE")
spDomain = cookies
}

var spUrl: String by Preference(url, cookies),定义一个委托属性spUrl,Preference委托,执行spUrl = cookies,会将这个setValue的动作委托到Preference类中的setValue。

    operator fun setValue(thisRef: Any?, property: KProperty<*>, value: T) {
putSharedPreferences(name, value)
}

其中value的值是cookies.如果要访问spUrl,那么,对应的getValue方法,会被委托到Preference中的getValue方法中去。

总结来说:

委托属性,就是将一个属性的getValue方法和setValue方法委托到另外一个代理类来实现。将属性的获取和设置隔离开来。

class Preference<T>(val name: String, private val default: T) {

    companion object {
private val file_name = "wan_android_file" private val prefs: SharedPreferences by lazy {
App.context.getSharedPreferences(file_name, Context.MODE_PRIVATE)
} /**
* 删除全部数据
*/
fun clearPreference() {
prefs.edit().clear().apply()
} /**
* 根据key删除存储数据
*/
fun clearPreference(key: String) {
prefs.edit().remove(key).apply()
} /**
* 查询某个key是否已经存在
*
* @param key
* @return
*/
fun contains(key: String): Boolean {
return prefs.contains(key)
} /**
* 返回所有的键值对
*
* @param context
* @return
*/
fun getAll(): Map<String, *> {
return prefs.all
}
} operator fun getValue(thisRef: Any?, property: KProperty<*>): T {
return getSharedPreferences(name, default)
} operator fun setValue(thisRef: Any?, property: KProperty<*>, value: T) {
putSharedPreferences(name, value)
} @SuppressLint("CommitPrefEdits")
private fun putSharedPreferences(name: String, value: T) = with(prefs.edit()) {
when (value) {
is Long -> putLong(name, value)
is String -> putString(name, value)
is Int -> putInt(name, value)
is Boolean -> putBoolean(name, value)
is Float -> putFloat(name, value)
else -> putString(name, serialize(value))
}.apply()
} @Suppress("UNCHECKED_CAST")
private fun getSharedPreferences(name: String, default: T): T = with(prefs) {
val res: Any = when (default) {
is Long -> getLong(name, default)
is String -> getString(name, default) ?: ""
is Int -> getInt(name, default)
is Boolean -> getBoolean(name, default)
is Float -> getFloat(name, default)
else -> deSerialization(getString(name, serialize(default)) ?: "")
}
return res as T
} /**
* 序列化对象 * @param person
* *
* @return
* *
* @throws IOException
*/
@Throws(IOException::class)
private fun <A> serialize(obj: A): String {
val byteArrayOutputStream = ByteArrayOutputStream()
val objectOutputStream = ObjectOutputStream(
byteArrayOutputStream
)
objectOutputStream.writeObject(obj)
var serStr = byteArrayOutputStream.toString("ISO-8859-1")
serStr = java.net.URLEncoder.encode(serStr, "UTF-8")
objectOutputStream.close()
byteArrayOutputStream.close()
return serStr
} /**
* 反序列化对象 * @param str
* *
* @return
* *
* @throws IOException
* *
* @throws ClassNotFoundException
*/
@Suppress("UNCHECKED_CAST")
@Throws(IOException::class, ClassNotFoundException::class)
private fun <A> deSerialization(str: String): A {
val redStr = java.net.URLDecoder.decode(str, "UTF-8")
val byteArrayInputStream = ByteArrayInputStream(
redStr.toByteArray(charset("ISO-8859-1"))
)
val objectInputStream = ObjectInputStream(
byteArrayInputStream
)
val obj = objectInputStream.readObject() as A
objectInputStream.close()
byteArrayInputStream.close()
return obj
} }

Kotlin委托属性(1)的更多相关文章

  1. kotlin委托属性

    fun main(arg: Array<String>) { val myClass1 = myClass1() myClass1.name="mycalsss1" v ...

  2. ViewBinding 与 Kotlin 委托双剑合璧

    请点赞关注,你的支持对我意义重大. Hi,我是小彭.本文已收录到 GitHub · Android-NoteBook 中.这里有 Android 进阶成长知识体系,有志同道合的朋友,关注公众号 [彭旭 ...

  3. Kotlin的属性委托:无上下文情况下Android的赋值(KAD 15)

    作者:Antonio Leiva 时间:Mar 9, 2017 原文链接:https://antonioleiva.com/property-delegation-kotlin/ 如我们在前面文章中读 ...

  4. kotlin 委托

    委托模式是软件设计模式中的一项基本技巧.在委托模式中,有两个对象参与处理同一个请求,接受请求的对象将请求委托给另一个对象来处理. Kotlin 直接支持委托模式,更加优雅,简洁.Kotlin 通过关键 ...

  5. Kotlin 委托(1)类委托、变量委托注意事项

    1.官方文档 英文: https://kotlinlang.org/docs/reference/delegation.html https://kotlinlang.org/docs/referen ...

  6. Kotlin代理属性--官方文档翻译

    代理属性 Delegated Properties 本文为个人翻译的Kotlin官方文档, 原文连接: Delegated Properties 一些特定的常见类型的属性, 尽管我们可以在每次需要的时 ...

  7. Kotlin 委托(2)变量委托是什么、自定义变量委托

    1.委托是什么? 1.1 官网示例 在每个变量委托的实现的背后,Kotlin 编译器都会生成辅助对象并委托给它. 假设委托如下, class C { var prop: Type by MyDeleg ...

  8. python cookbook第三版学习笔记十七:委托属性

    我们想在访问实例的属性时能够将其委托到一个内部持有的对象上,这经常用到代理机制上 class A:     def spam(self,x):         print("class_A: ...

  9. kotlin 委托类的初始化函数

    import java.beans.AppletInitializer import kotlin.reflect.KProperty fun main(arg: Array<String> ...

  10. Android kotlin静态属性、静态方法

    只需要用 companion object 包裹相应代码块即可.以静态属性为例: class Constants { companion object { val BASE_URL = "h ...

随机推荐

  1. 好用!这些工具国庆一定要研究下「GitHub 热点速览」

    再过 3 天就要开始一年最长的假期--国庆长假了,这次除了宅家.出游之外,多了一个新选项:研究下哪些项目可以安排上,来辅助自己的日常开发. 你觉得一周获得 4k star 的 hyperdx 如何,它 ...

  2. 记一次 .NET 某拍摄监控软件 卡死分析

    一:背景 1. 讲故事 今天本来想写一篇 非托管泄露 的生产事故分析,但想着昨天就上了一篇非托管文章,连着写也没什么意思,换个口味吧,刚好前些天有位朋友也找到我,说他们的拍摄监控软件卡死了,让我帮忙分 ...

  3. Springboot+Mybatisplus+ClickHouse集成

    核心依赖引入 <dependency> <groupId>ru.yandex.clickhouse</groupId> <artifactId>clic ...

  4. 教学法学期末考试MOOC01

    期末考试 返回 期末考试试卷为客观题,总分为100分,占课程成绩的40%.其中包含16道单选题,2道多选题.共18道题.单选题每道5分,多选题每道10分,限时90分钟完成.  倒计时: 01:13:4 ...

  5. 查漏补缺,这些热门开源项目你都知道么?「GitHub 热点速览」

    本期热点速览的周榜部分的项目,基本上每周都会在 GitHub Trending 见到它们的身影,因为它们实在太火了.一般来说,这些火爆的项目大家都耳熟能详,但是为了防止有些小伙伴不怎么逛 GitHub ...

  6. [GXYCTF 2019]BabyUpload

    看到题目是一个文件上传 就先随便传的东西试试,看有什么过滤之类的 上传一个一句话木马,提示后缀名不能为ph 随便上传了带有一句话木马的图片,发现上传成功,但这个图片不能直接利用,要先上传一个.htac ...

  7. 使用PasteSpider把你的代码升级到服务器的Docker/Podman上,K8S太庞大,PasteSpider极易上手!

    如果你的服务器的内存小于16GB,那么K8S就和你无缘了,但是你可以使用PasteSpider来实现发布你的项目到服务器上! PasteSpider是一个运维工具,使用NET编写的,部署于服务器的Do ...

  8. Java核心知识体系5:反射机制详解

    Java核心知识体系1:泛型机制详解 Java核心知识体系2:注解机制详解 Java核心知识体系3:异常机制详解 Java核心知识体系4:AOP原理和切面应用 1 介绍 无论是那种语言体系,反射都是必 ...

  9. 18.1 Socket 原生套接字抓包

    原生套接字抓包的实现原理依赖于Windows系统中提供的ioctlsocket函数,该函数可将指定的网卡设置为混杂模式,网卡混杂模式(Promiscuous Mode)是常用于计算机网络抓包的一种模式 ...

  10. 机器学习从入门到放弃:硬train一发手写数字识别

    一.前言 前面我们了解了关于机器学习使用到的数学基础和内部原理,这一次就来动手使用 pytorch 来实现一个简单的神经网络工程,用来识别手写数字的项目.自己动手后会发现,框架里已经帮你实现了大部分的 ...