如何在 Kotlin 中实现这个 Java 接口?

36

Kotlin没有原始数据类型,那么如何实现这个接口呢?

public interface A {
  @NotNull Object get(@NotNull Integer i);
  @NotNull Object get(int i);
}

由于Java代码是编译后的类文件存储在二进制库中,因此我无法更改其内容。


2
fun get(i: Integer /* or Integer? */) = ...; fun get(i: Int) = ... 的问题是什么? - Alexey Romanov
5个回答

28

如果像@zsmb13所述的单一实现不足以满足您的需求,您需要在Kotlin中为这两种方法创建单独的实现,则可以添加一个中间接口来覆盖接受Integer参数的方法,并将其变为可空参数:

private interface IntermediateA : A {
    override fun get(i: Int?): Any
}

实现这个接口而不是原来的A,Kotlin编译器将区分这两个方法,允许你按照以下方式重写它们:

class C : IntermediateA {
    override fun get(i: Int) = "primitive"
    override fun get(i: Int?) = "boxed"
}

val a: A = C()
println(a.get(1)) // primitive
println(a.get(1 as Int?)) // boxed
如果您可以访问Java代码,您可以通过向接受装箱类型的方法添加nullability注释来修复此问题:
Object get(@Nullable Integer i);

Kotlin编译器能够理解不同类型的可空性注释,这里是列表


11

仅实现一个以Int作为参数的方法即可,该方法可从Kotlin或Java中调用。

class B : A {

    override fun get(i: Int): Any {
        return "something"
    }

}

如果你反编译字节码,你会看到Kotlin编译器聪明地创建了这两个方法之一只是重定向到真正的实现。

Decompiled bytecode example

可能出现的问题之一是你无法使该方法接受Int?,如果从Java中这样调用它:.intValue()就会导致NullPointerException崩溃。

B b = new B();
Integer i = null;
b.get(i);

我不确定是否有一种方法解决这个用例。

编辑:hotkey的答案中包含其余的答案。


如果我有两个完全不同的实现,取决于它是 int 还是 Integer,那该怎么办?在 Kotlin 中如何区分它们? - azizbekian
在这种情况下似乎不可能实现。一般来说,您可以通过声明一个接受 Int 处理基元类型的方法和另一个接受 Int? 处理装箱类型的方法来区分它们。 - zsmb13
好的,我明白你的意思。但是我不明白为什么装箱类型的值,只要它的值不是“null”,就不会立即转换为 Int - azizbekian
1
有一种方法,但需要将Java方法参数注释为@Nullable。如果没有访问Java代码的权限,似乎只能通过中间Java接口实现,详见其他答案。 - hotkey
1
实际上,一个 Kotlin 中间接口就足够了(只需覆盖一个带有 Int? 参数类型的函数)。 - hotkey

4
在Kotlin中,我们可以声明:
  • 基本类型 int 为:Int
  • 包装类型 int 为:Int?
你的接口可以简化为:
private interface ModifiedA : A {
    override fun get(i: Int?): Any
}

在Kotlin中,如果你实现了这个修改后的接口,那么Kotlin会为你提供两种方法来重写。一种是针对原始类型的,另一种是针对装箱类型的。

class ImplementationOfA : ModifiedA {
    override fun get(i: Int)
    override fun get(i: Int?)
}

0

添加以下代码行以在 Kotlin 中实现接口

class abc : AppCompatActivity(), interface 1, interface 2,
{
override fun get(i: Int?): Any
}

目前你的回答不够清晰,请编辑并添加更多细节,以帮助其他人理解它如何回答问题。你可以在帮助中心找到有关如何编写好答案的更多信息。 - Community
AppCompatActivity 有什么相关性? - ice1000

0

我用Java写了一个简单的演示。

然后在IntelliJ IDEA或Android Studio中使用Kotlin插件将其转换为Kotlin。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接