IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 移动开发 -> 一天一个小知识:KT扩展 -> 正文阅读

[移动开发]一天一个小知识:KT扩展

?

让我们从用法到分类讲起

扩展?扩展什么呢?当然是扩展类中的属性和方法 这里厉害?看段代码吧?

1//?这就是扩展函数
2fun?String.pandaer()?{
3????println("pandaer杂货铺中的$this")
4}
5
6fun?main()?{
7????"android".pandaer()
8}

感觉扩展函数没什么特别的,和普通函数相比不就是多了 ClassType. 这里就是String. 这个我们便给他一个名字:接收者 但是如果真的能扩展一个类的属性和方法不就乱套了吗。那岂不是我想要扩展谁就扩展谁。

通过反编译看原理

 1//?上述代码编译而来
 2public?final?class?KTXKt?{
 3???public?static?final?void?pandaer(@NotNull?String?$this$pandaer)?{
 4??????Intrinsics.checkNotNullParameter($this$pandaer,?"$this$pandaer");
 5??????String?var1?=?"pandaer杂货铺中的"?+?$this$pandaer;
 6??????System.out.println(var1);
 7???}
 8
 9???public?static?final?void?main()?{
10??????pandaer("android");
11???}
12
13???//?$FF:?synthetic?method
14???public?static?void?main(String[]?var0)?{
15??????main();
16???}
17}

观察逻辑 pandaer() 方法变成了一个静态方法,而接收者变成了该函数的参数。所以所谓的扩展又是语法层面的,底层的实现就是一个静态方法(顶层扩展)这让我不禁想到一句话 理想是丰满的现实是骨感的。

从底层原理看优缺点

因为底层的实现并不是真正的去扩展某个类,所以我们定义的扩展函数和扩展属性都不能被子类继承, 并非真实扩展所以就存在访问作用域的限制 拿上面代码举例,如果我要在我的pandaer()函数中调用接收者类型的私有成员,是不可能的,因为底层实现限制了这一点,传递的是一个实实在在的接收者对象,顶多调用公开的方法

?

前面都是扩展函数和扩展属性都有的缺点,而扩展属性还有一个缺点:无状态

这个我们还是从底层实现来看

 1//kt
 2class?Pan?{
 3????var?name?:?String?=?"xixi"
 4????private?fun?cry()?{
 5????????println("Cry")
 6????}
 7????fun?smile()?{
 8????????println("smile")
 9????}
10}
11
12val?Pan.age?:?String
13????get()?=?name
14
15//java
16public?final?class?KTXKt?{
17???@NotNull
18???public?static?final?String?getAge(@NotNull?Pan?$this$age)?{
19??????Intrinsics.checkNotNullParameter($this$age,?"$this$age");
20??????return?$this$age.getName();
21???}
22}

属性最后还是被转换成了静态函数。所以无论是扩展方法还是扩展属性底层的实现都是静态方法(顶层扩展)

所以无状态就好理解了,就是不能自己存储数据 用kt话说没有支持字段

总结一下:

缺点:

  1. 不能被继承
  2. 访问作用域受限
  3. 无状态

从KT源码的设计中看优点

?

每次你没有看错KT中的源码只有45行,你会发现这些函数不够我们用啊,不是还有一些函数吗?答案是他们在Strings.kt中 在真正的String类的源码设计中只保留最核心的逻辑,一些功能性的逻辑用扩展函数来代替了。所以这就是第一个优点 关注点分离 源码的设计就是将核心逻辑 和 功能性的逻辑分离

第二个优点 : 减少模板代码

1fun?Date.format(format:String?=?"EEE,yyyy-mm-dd")?:?String?{
2????val?simFormat?=?SimpleDateFormat(format)
3????return?simFormat.format(this.time)
4}
5fun?main()?{
6????println(Date().format())
7}

比如这个例子,以前我们要格式化时间要使用一个格式类,现在直接一个扩展函数就解决问题了。

让我们补充讲讲类中的扩展

?

看上面这个代码,我在类中虽然可以写扩展函数和扩展属性,但是他好像被困在Pan类中了

看底层实现

 1public?final?class?Pan?{
 2???private?final?String?name?=?"pandaer";
 3
 4???private?final?void?f2()?{
 5??????String?var1?=?"f1";
 6??????System.out.println(var1);
 7???}
 8
 9???public?final?void?f1(@NotNull?String?$this$f1)?{
10??????Intrinsics.checkNotNullParameter($this$f1,?"$this$f1");
11??????this.f2();
12???}
13
14???@NotNull
15???public?final?String?getNameKtx(@NotNull?String?$this$nameKtx)?{
16??????Intrinsics.checkNotNullParameter($this$nameKtx,?"$this$nameKtx");
17??????return?this.name;
18???}
19
20???public?final?void?text()?{
21??????String?xixi?=?this.getNameKtx("xixi");
22??????this.f1("xixi");
23???}
24}

很明显,扩展方法和属性一如既往的变成了方法不过这次是属于Pan类的成员方法,所以才被关在了Pan中。

从优缺点中看应用场景

关注点分离 可以让我们和源码设计一样 将核心逻辑和功能性的逻辑分离

比如用扩展方法替代以前在Java中的工具类

如果你还知道更多的应用场景不妨告诉我😄我们一起学习进步

  移动开发 最新文章
Vue3装载axios和element-ui
android adb cmd
【xcode】Xcode常用快捷键与技巧
Android开发中的线程池使用
Java 和 Android 的 Base64
Android 测试文字编码格式
微信小程序支付
安卓权限记录
知乎之自动养号
【Android Jetpack】DataStore
上一篇文章      下一篇文章      查看所有文章
加:2022-09-21 00:40:23  更:2022-09-21 00:44:14 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/25 5:45:25-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码