Kotlin编程实践-【Java如何调用Kotlin中带默认值参数的函数】

问题

如果你有一个带有默认参数值的 Kotlin 函数,如何从 Java 调用它而无须为每个参数显式指定值?

方案

为函数添加注解@JvmOverloads。

也就是为Java添加重载方法,这样Java调用Kotlin的方法时就不用传递全部的参数了。

示例

在 Kotlin 中定义一个函数,函数指定了多个带默认值的参数,如下:

kotlin 复制代码
/**
 * kotlin中模拟定义一个addUser函数
 *
 * 参数 name 必需的,age 和 address有默认值, 其中address可空
 */
fun addUser(
    name: String,
    age: Int = 18,
    address: String? = null,
) {
    println("新增User, 信息如下:")
    println("name is $name, age is $age, address is $address")
    println("==================================")
}

在 Kotlin 中如果调用这个函数,可以指定一个、两个、三个参数来调用它,如下:

kotlin 复制代码
fun main() {
    // name必传, age 和 address 使用默认值
    addUser("张三")
    // address使用默认值
    addUser("李四", age = 20)
    // age使用默认值, address可空所以这里可以传递null
    addUser("王五", address = null)
    // 都不使用默认值
    addUser("赵六", 30, "北京")
}

执行结果如下:

新增User, 信息如下:

name is 张三, age is 18, address is null

==================================

新增User, 信息如下:

name is 李四, age is 20, address is null

==================================

新增User, 信息如下:

name is 王五, age is 18, address is null

==================================

新增User, 信息如下:

name is 赵六, age is 30, address is 北京

==================================

然而,Java方法不支持默认参数,所以当在Java中调用这个函数时,必须提供所有的参数,如下:

java 复制代码
public static void main(String[] args) {
    // 缺少任何一个参数就会报错
    // KotlinDemoKt.addUser("java", 100);
    // 必须传递三个参数
    KotlinDemoKt.addUser("java", 100, null);
}

打印结果如下:

新增User, 信息如下:

name is java, age is 100, address is null

==================================

从截图中也可以看出,Java调用的时候,addUser方法需要传递三个参数才行。

如果将注解 @JvmOverloads 添加到函数中,生成的类将支持所有的函数重载。改造如下:

给 Kotlin 中定义的函数加上注解 @JvmOverloads ,此时再回到 Java 中调用发现:

此时 Java 中调用 Kotlin 的函数 addUser,就有了三个方法可调用了,这就是注解 @JvmOverloads 的作用,让它看起来就像是 Java 中的重载方法。

同样可以对 Kotlin 中的构造函数做出这样的操作,如下,在 Person 类中生成三个构造方法:

Kotlin 中的类此时没有添加注解 @JvmOverloads , 所以 Java 创建类对象的时候,还是必须要传递三个参数的初始值。

加上注解之后,如下:

如上,Java 中实例化类可以使用不同参数完成了。

注意:Kotlin 中的主构造函数,没有注解和修饰符的时候,可以省略关键字 constructor,但因为此时有注解 @JvmOverloads,所以需要加上关键字 constructor。

总结

考虑到Java没有参数默认值的概念,当你从 Java 中调用 Kotlin 函数的时候必须显式地指定所有参数值。

如果需要从 Java 代码中做频繁的调用,而且希望它能对Java的调用者更简便,可以用 @JvmOverloads 注解它。这个指示编译器生成Java重载函数,从最后一个开始省略每个参数

相关推荐
心勤则明3 分钟前
用 SpringAIAlibab 让高频问题实现毫秒级响应
java·人工智能·spring
anzhxu4 分钟前
SpringBoot 3.x 整合swagger
java·spring boot·后端
gechunlian884 分钟前
Spring Security 官网文档学习
java·学习·spring
小江的记录本7 分钟前
【Bean】JavaBean(原生规范)/ Spring Bean 【重点】/ 企业级Bean(EJB/Jakarta Bean)
java·数据库·spring boot·后端·spring·spring cloud·mybatis
qqty12177 分钟前
spring loC&DI 详解
java·spring·rpc
中国胖子风清扬12 分钟前
Camunda 8 概念详解:梳理新一代工作流引擎的核心概念与组件
java·spring boot·后端·spring cloud·ai·云原生·spring webflux
闻哥13 分钟前
MySQL InnoDB 缓存池(Buffer Pool)详解:原理、结构与链表管理
java·数据结构·数据库·mysql·链表·缓存·面试
殷紫川15 分钟前
告别臃肿部署!Java Serverless 函数计算架构全解与实战选型指南
java·架构
陆业聪22 分钟前
让 Android 里的 AI 真正「干活」:Function Calling 工程实现全解
android·ai·kotlin
孟陬28 分钟前
为什么国外技术大神都爱自己搭博客,而国内程序员却挤在微信公众号或掘金?
java·typescript·前端框架