我正在学习Kotlin,我在功能上遇到了一些麻烦。 我正在尝试创建带有泛型参数的功能接口之类的东西。 在Java中,我将创建以下内容:
@FunctionalInterface
public interface Foo<T extends Bar> {
String something(T arg);
}
然后我可以在其他类似地方使用它(假设Person
扩展了Bar
:
Foo<Person> f = p -> p.toString();
您如何用Kotlin编写此书?
我尝试的第一件事是使用这样的类型别名:
typealias Foo<T> = (T) -> String
但是,当我将绑定添加到类型参数时,它停止工作:
typealias Foo<T: Bar> = (T) -> String // Error: Bounds are not allowed on type alias parameters
第二种方法是编写一个扩展函数类型的接口:
interface Foo<T: Bar> : (T) -> String
但是,现在我不知道如何使用此实例化lambda函数。当我像这样从中创建类时,它将起作用:
class Something: Foo<Person> {
override fun invoke(p: Person): String {
return p.toString()
}
}
val f = Something()
但这是一个很大的开销,我确信必须有一个更好的解决方案。
那么我如何定义一个可以被许多支持通用参数且在kotlin中有界限的函数重用的函数签名?
答案 0 :(得分:4)
在大多数时候(总是?),在接收它的函数的参数中定义lambda的类型就足够了。
例如:
open class Bar
class Person: Bar()
var f = { p: Person -> p.toString() }
fun <T : Bar> withFoo(block: (T) -> String) { }
fun <T : Bar> otherFoo(block: (T) -> String) { }
fun main() {
withFoo(f)
otherFoo(f)
}
Kotlin文档指出的相同方式: “由于Kotlin具有适当的功能类型,因此不需要将功能自动转换为Kotlin接口的实现,因此不受支持。”
请参见https://kotlinlang.org/docs/reference/java-interop.html#sam-conversions