Kotlin @JvmInline class 破坏了 class 方法名称
Kotlin @JvmInline class broke class method names
在使用由 @JvmInline
注释的 Kotlin 值 class 时遇到问题
这是一个例子:
@JvmInline
value class TestClass(val id: String)
interface TestInterface {
fun doSomething(aVal: TestClass)
fun callSomething(aVal: String)
}
fun main() {
val clazz = TestInterface::class.java
clazz.methods.forEach { println(it) }
}
结果输出:
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething-Qkb7kKY(java.lang.String)
预期输出:
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething(java.lang.String)
关于如何在不切换到 数据的情况下解决此问题的任何想法 class?
值 类 在运行时不存在 。
正如您从输出中看到的,方法的签名是 TestInterface.doSomething-Qkb7kKY(java.lang.String)
。由于值 类 本质上是其值的运行时包装器,因此该方法的真正签名有一个 String 参数。在编译时,使用单个 String
参数向此方法添加另一个重载是完全可以的,在运行时,这会导致冲突。让我们扩展您的示例;
@JvmInline
value class TestClass(val id: String)
interface TestInterface {
fun doSomething(aVal: TestClass)
fun doSomething(aVal: String)
fun callSomething(aVal: String)
}
fun main() {
val clazz = TestInterface::class.java
clazz.methods.forEach { println(it) }
}
以上内容的输出如下,因此如果同名会发生冲突;
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething(java.lang.String)
public abstract void TestInterface.doSomething-Qkb7kKY(java.lang.String)
在使用由 @JvmInline
注释的 Kotlin 值 class 时遇到问题这是一个例子:
@JvmInline
value class TestClass(val id: String)
interface TestInterface {
fun doSomething(aVal: TestClass)
fun callSomething(aVal: String)
}
fun main() {
val clazz = TestInterface::class.java
clazz.methods.forEach { println(it) }
}
结果输出:
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething-Qkb7kKY(java.lang.String)
预期输出:
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething(java.lang.String)
关于如何在不切换到 数据的情况下解决此问题的任何想法 class?
值 类 在运行时不存在 。
正如您从输出中看到的,方法的签名是 TestInterface.doSomething-Qkb7kKY(java.lang.String)
。由于值 类 本质上是其值的运行时包装器,因此该方法的真正签名有一个 String 参数。在编译时,使用单个 String
参数向此方法添加另一个重载是完全可以的,在运行时,这会导致冲突。让我们扩展您的示例;
@JvmInline
value class TestClass(val id: String)
interface TestInterface {
fun doSomething(aVal: TestClass)
fun doSomething(aVal: String)
fun callSomething(aVal: String)
}
fun main() {
val clazz = TestInterface::class.java
clazz.methods.forEach { println(it) }
}
以上内容的输出如下,因此如果同名会发生冲突;
public abstract void TestInterface.callSomething(java.lang.String)
public abstract void TestInterface.doSomething(java.lang.String)
public abstract void TestInterface.doSomething-Qkb7kKY(java.lang.String)