从Java访问Kotlin扩展function

有没有可能从Java代码访问扩展函数?

我在Kotlin文件中定义了扩展function。

package com.test.extensions import com.test.model.MyModel /** * */ public fun MyModel.bar(): Int { return this.name.length() } 

MyModel是一个(生成的)java类。 现在,我想在我的正常的java代码中访问它:

 MyModel model = new MyModel(); model.bar(); 

但是,这是行不通的。 IDE将无法识别bar()方法,编译失败。

kotlin的静态函数使用了什么工作:

 public fun bar(): Int { return 2*2 } 

通过使用import com.test.extensions.ExtensionsPackage所以我的IDE似乎configuration正确。

我search了kotlin文档中的整个Java-interop文件,也search了很多,但是我找不到它。

我究竟做错了什么? 这甚至有可能吗?

在一个文件中声明的所有Kotlin函数将被默认编译为同一个包中的类中的静态方法,并且源自Kotlin源文件的名称(首字母大写和“.kt”扩展名replace为“Kt”后缀) 。 为扩展函数生成的方法将具有扩展函数接收器types的附加第一个参数。

将它应用到原始问题,Java编译器将会看到名为example.kt的 Kotlin源文件

 package com.test.extensions public fun MyModel.bar(): Int { /* actual code */ } 

就好像下面的Java类被声明一样

 package com.test.extensions class ExampleKt { public static int bar(MyModel receiver) { /* actual code */ } } 

从Java的angular度来看,扩展类没有任何反应,你不能只用点语法来访问这样的方法。 但是它们仍然可以作为普通的Java静态方法调用:

 import com.test.extensions.ExampleKt; MyModel model = new MyModel(); ExampleKt.bar(model); 

静态导入可以用于ExampleKt类:

 import static com.test.extensions.ExampleKt.*; MyModel model = new MyModel(); bar(model); 

Kotlin顶级扩展函数被编译为Java静态方法。

给定包含foo.bar Kotlin文件Extensions.kt包含:

 fun String.bar(): Int { ... } 

等效的Java代码将是:

 package foo.bar; class ExtensionsKt { public static int bar(String receiver) { ... } } 

除非,即Extensions.kt包含该行

 @file:JvmName("DemoUtils") 

在这种情况下,Java静态类将被命名为DemoUtils

在Kotlin中,扩展方法可以用其他方式声明。 (例如,作为成员函数或作为伴随对象的扩展。)我将尽力在以后的日子扩大这个答案。

据我所知,这是不可能的。 从我阅读扩展文档看来,

 public fun MyModel.bar(): Int { return this.name.length() } 

创build一个签名的新方法

 public static int MyModelBar(MyModel obj) { return obj.name.length(); } 

然后,Kotlin将函数映射到forms为myModel.bar()调用,其中如果在MyModel类中找不到bar()MyModel查找与输出的签名和命名scheme相匹配的静态方法。 请注意,这只是他们关于扩展名被静态导入的语句的一个假设,而不是覆盖已定义的方法。 我的源头还不够深入,无法确定。

所以,假设上述情况是真的,Kotlin扩展就没有办法从简单的旧Java代码中调用,因为编译器只会看到一个未知的方法被调用到一个对象上并出错。