当前位置: 首页 > 面试题库 >

为什么在Java中实现Kotlin函数以返回Unit时必须返回Unit.INSTANCE?

淳于健
2023-03-14
问题内容

如果我有Kotlin功能

fun f(cb: (Int) -> Unit)

我想f从Java 打电话,我必须这样做:

f(i -> {
     dosomething();
     return Unit.INSTANCE;
});

看起来很丑 f(i -> dosomething());由于UnitKotlin void中的Java 等同于Java ,为什么我不能这样写呢?


问题答案:

UnitKotlin void中的Java 在大多数情况下与Java中的等效,但是仅在JVM规则允许的情况下才如此。

Kotlin中的功能类型由以下接口表示:

public interface Function1<in P1, out R> : Function<R> {
    /** Invokes the function with the specified argument. */
    public operator fun invoke(p1: P1): R
}

在声明时(Int) -> Unit,从Java的角度来看,这等效于Function<Integer, Unit>。这就是为什么您必须返回一个值。要变通解决此问题,在Java中有两个单独的接口Consumer<T>Function<T, R>当您没有返回值/没有返回值时。

Kotlin的设计者决定放弃功能接口的重复,而是依靠编译器“魔术”。如果在Kotlin中声明一个lambda,则不必返回值,因为编译器会为您插入一个值。

为了使您的生活更轻松一点,你可以写一个封装了一个辅助方法Consumer<T>Function1<T, Unit>

public class FunctionalUtils {
    public static <T> Function1<T, Unit> fromConsumer(Consumer<T> callable) {
        return t -> {
            callable.accept(t);
            return Unit.INSTANCE;
        };
    }
}

用法:

f(fromConsumer(integer -> doSomething()));

有趣的事实:UnitKotlin编译器的特殊处理是您可以编写如下代码的原因:

fun foo() {
    return Unit
}

要么

fun bar() = println("Hello World")

两种方法void在生成的字节码中都有返回类型,但是编译器足够聪明,可以弄清楚这一点,并允许您使用返回语句/表达式。



 类似资料:
  • 如果我有一个Kotlin函数 我想从Java调用,我必须这样做: 看起来很难看。为什么我不能像

  • 问题内容: 我是一名编程初学者,对函数的返回值有疑问。 我正在学习Java。 我已经附上了我的书中具有经典选择排序功能的代码。 现在显然来自本书的代码可以正常工作。但是,主要功能中的以下三行是我的问题的基础: int [] a = new int [] {1,9,2,8,3,7,4,6​​,5}; 排序(a); if(ascending(a))System.out.println(“ Works”

  • 问题内容: 除了使用关键字调用构造函数时,Java语言中的语句可以返回值的确切情况是什么? 例: 如果我没记错的话,如果它是一个非函数原语,将被返回。否则返回。这个对吗? 换句话说,什么值可以引起? 问题答案: 确切的条件在内部属性上进行了描述,该属性由操作员使用: 来自ECMA-262第3条。版本规格: 13.2.2 调用对象的属性时,将执行以下步骤: 创建一个新的本机ECMAScript对象。

  • 问题内容: 即使正则表达式应返回true,程序也不会退出。代码有什么问题? 问题答案: 仅当整个字符串与正则表达式匹配时才返回。在你的情况下,你的正则表达式仅代表 一个 字符不是,或。 我怀疑您要检查字符串是否包含您在正则表达式中描述的这些特殊字符之一。在这种情况下,请将您的正则表达式括起来,以使正则表达式匹配整个字符串。哦,您不必逃脱character class内部。

  • 问题内容: 在我的Ajax请求(使用jQuery)中,我返回了JSON响应。 所以json.Html将有一个HTML字符串,我想在div内追加。 在服务器端,我是否必须转义HTML? 在我的MVC动作中,我返回: 问题答案: 另一种解决方案是仅返回HTML并使用jQuery的: 不过,按照自己的方式进行操作,只需转义双引号和反斜杠即可。 该规范易读且简短。

  • 问题内容: 如果我在构造函数中返回一些值或对象,那么var会得到什么? 在两种情况下都会得到什么n? 其实这是一个测验问题,答案是什么? 自定义对象构造函数返回什么? a)新实例化的对象 b)未定义-构造函数不返回值 c)不论return语句是 d)等于return语句是什么;新实例化的对象(如果没有return语句) 问题答案: 我发现了这个很棒的链接: 上面提到的第二点魔术是构造函数返回特定的