尽管内联 lambda 具有 return,但具有块主体的函数中需要 'return' 表达式

A 'return' expression required in a function with a block body despite inlined lambda which has the return

我正在尝试创建一个内联的 try-catch 辅助函数,但由于 return 语句出现在内联的 lambda 中,所以 运行 出现编译错误。下面是一些演示相同问题的代码

fun isStringEmpty(myString: String): Boolean {
    stringOpHelper { 
        return myString.length == 0
    }
}
inline fun <T> stringOpHelper(fn: () -> T) {
    println("performing string operation")
    fn()
}

如果在内联函数调用或抛出异常后添加 return,这将编译出预期的效果,但该代码应该无法访问。例如:

fun isStringEmpty(myString: String): Boolean {
    stringOpHelper { 
        return myString.length == 0
    }
    TODO("this is actually unreachable")
}
inline fun <T> stringOpHelper(fn: () -> T) {
    println("performing string operation")
    fn()
}

我的期望是编译器会看到 stringOpHelper 总是调用 fn()isStringEmpty 中的 fn 总是 returns,所以内联stringOpHelper 总是调用 returns.

是否可以通过避免在调用函数中出现无法访问的异​​常/return 的方式来定义内联辅助函数?否则,这是不可能的原因是什么?

有一种用于此类目的的机制称为 contracts,但此功能是实验性的,其用法必须用 @ExperimentalContracts@OptIn(ExperimentalContracts::class)

标记
@OptIn(ExperimentalContracts::class)
inline fun <T> stringOpHelper(fn: () -> T) {
    contract {
        callsInPlace(fn, kotlin.contracts.InvocationKind.EXACTLY_ONCE)
    }
    println("performing string operation")
    fn()
}