Kotlin1.8新增特性,进来了解一下

大家好,之前我已经写过了分析kotlin1.5、1.6、1.7、1.9插件版本新增的一些特性,唯独kotlin1.8的特性还没好好讲讲,本篇文章就带大家好好分析下kotlin1.8新增了那些特性,能对我们日常开发带来哪些帮助。

其中Kotlin1.8.0提供的特性有限,本篇文章主要是分析Kotlin1.8.20提供的一些新特性。下面是支持该插件的IDE对应版本:

一. 提供性能更好的Enum.entries替代Enum.values()

在之前,如果我们想遍历枚举内部元素,我们通常会写出以下代码:

enum class Color(val colorName: String, val rgb: String) {
    RED("Red", "#FF0000"),
    ORANGE("Orange", "#FF7F00"),
    YELLOW("Yellow", "#FFFF00")
}


fun main() {
    Color.values().forEach {
        println("${it.rgb}--${it.colorName}--${it.name}")
    }
}

但是不知道大家是否清楚,Color.values() 其实存在性能问题,换句话说,每调用一次该方法,就会触发重新分配一块内存,如果调用的频率过高,就很可能引发内存抖动

我们可以反编译下枚举类简单看下原因:

Color.values()每次都会调用Object.clone()方法重新创建一个新的数组,这就是上面说的潜在的性能问题,github上也有相关的问题链接,感兴趣的可以看下:HttpStatus.resolve allocates HttpStatus.values() once per invocation

同时Color.values()返回的是一个数组,而在我们大多开发场景中,可能集合使用的频率更高,这就可能涉及到一个数组转集合的操作。

基于以上考虑,Kotlin1.8.20官方提供了一个新的属性:Color.entries这个方法会预分配一块内存并返回一个不可变集合,多次调用也不会产生潜在的性能问题

我们简单看下使用:

fun main() {

    Color.entries.forEach {
        println("${it.rgb}--${it.colorName}--${it.name}")
    }
}

输出:

同时我们也可以从反编译的代码中看出区别:

不会每次调用都重新分配一块内存并返回。

如果想要使用这个特性,可以加上下面配置:

compileKotlin.kotlinOptions {
    languageVersion = "1.9"
}

另外多说一下,IntelliJ IDEA 2023.1版本也会检测代码中是否存在Enum.values()的使用,存在就提示使用Enum.entries代替。

二. 允许内联类声明次级构造函数

内联类在Kotlin1.8.20之前是不允许带body的次级构造函数存在的,也就是说下面的代码运行会报错:

@JvmInline
value class Person( val fullName: String) {
    constructor(name: String, lastName: String) : this("$name $lastName") {
        check(lastName.isNotBlank()) {
            "Last name shouldn't be empty"
        }
    }
}


fun main() {
    println(Person("a", "b").fullName)
}

运行看下结果:

如果没有次级构造函数body,下面这样写是没问题的:

    constructor(name: String, lastName: String) : this("$name $lastName") 

如果想要支持带body的次级构造函数,只需要在kotlin1.8.20插件版本上和上一个特性一样增加languageVersion = "1.9"配置即可。

然后上面的代码块运行就没问题了,我们看下输出:

fun main() {

    println(Person("a", "").fullName)
}

准确的执行了次级构造函数body内的逻辑。

三. 支持java synthethic属性引用

这个特性用文字不好解释,我们直接通过代码去学习下该特性。

当前存在一个类Person1

public class Person1 {
    private String name;
    private int age;

    public Person1(String name, int age) {
        this.name = name;
        this.age = age;
    }


    public String getName() {
        return name;
    }

    public int getAge() {
        return age;
    }
}

在Kotlin1.8.20之前,以下这种写法是会报错的:

而是必须改成sortedBy(Person1::getAge)才能运行通过。

和上面特性一样,如果想要支持Person1::age这种引用方式,只需要在kotlin1.8.20插件版本上和上一个特性一样增加languageVersion = "2.1"配置即可。

PS:请注意,Kotlin官方网站提示配置languageVersion = "1.9" 就能使用上面的实验特性,但是编译器还是提示报错,然后你找报错提示信息改成了languageVersion = "2.1" 就正常了。

四. 新Kotlin K2编译器的更新

就是说目前Kotlin K2编译器还是一个实验阶段,不过Kotlin官方在其stable的路上又增加了一些更新:

  1. 序列化插件的预览版本;
  2. JS IR编译器的alpha支持;
  3. Kotlin2.0版本特性的引入;

如果大家想要体验下最新版的Kotlin K2编译器,增加配置:languageVersion ="2.0"即可。

五. Kotlin标准库支持AutoCloseable

这个AutoCloseable 接口就是用来支持资源关闭的,搭配提供的use扩展函数,就能帮助我们在资源流使用完毕后自动关闭。

Kotlin之所以在标准库中支持,应该是想要支持多平台吧。

六. Kotlin标准库支持Base64编解码

这里不做太多介绍,看下面的使用例子即可:

七. Kotlin标准库@Volatile支持Kotlin/Native

@Volatile注解在Kotlin/JVM就是保证线程之间可见性以及有序性的,kotlin官方在Kotlin/Native中也支持了该注解使用,有兴趣的可以实战试下效果。

总结

本篇文章主要是介绍了Kotlin1.8版本新增的一些特性,主要挑了一些我能理解的、常用的一些特性拉出来介绍,希望能对你有所帮助。

历史文章

两个Kotlin优化小技巧,你绝对用的上

浅析一下:kotlin委托背后的实现机制

Kotlin1.9.0-Beta,它来了!!

聊聊Kotlin1.7.0版本提供的一些特性

聊聊kotlin1.5和1.6版本提供的一些新特性

kotlin密封sealed class/interface的迭代之旅

优化@BuilderInference注解,Kotlin高版本下了这些“毒手”!

@JvmDefaultWithCompatibility优化小技巧,了解一下~

© 版权声明
THE END
喜欢就支持一下吧
点赞0

Warning: mysqli_query(): (HY000/3): Error writing file '/tmp/MYw0pMum' (Errcode: 28 - No space left on device) in /www/wwwroot/583.cn/wp-includes/class-wpdb.php on line 2345
admin的头像-五八三
评论 抢沙发
头像
欢迎您留下宝贵的见解!
提交
头像

昵称

图形验证码
取消
昵称代码图片