如何指定"accepts generic sub-type of a generic type"?
How to specify "accepts generic sub-type of a generic type"?
我正在尝试实现接受通用参数的函数定义,只要它扩展了另一个特定的通用类型。简而言之;参数 A 必须扩展参数 B,其中 A 和 B 都是通用的。
下面是我的示例
abstract class Endpoint<T>(
) {
private val myList: MutableMap<Class<T>, MutableList<((T) -> Unit)>> = mutableMapOf()
fun addToList(
index: Class<E>, <-- E extends T
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
}
用法示例为
部分封印class
sealed class MainSealedClass {
data class ChildClass(val someParam: Int): MainSealedClass()
}
以及函数调用
anEndpointInstance.addToList(MainSealedClass.ChildClass::class.java, "some value")
我希望不必在抽象 class 声明中定义 E,因为 T 已经在那里定义了。
我也尝试过以下操作:
将 myList 定义为接受扩展 T 的键
val myList: MutableMap<Class<in T>, MutableList<String>>
将 E 定义为 T 类型(找不到如何在函数中指定它扩展 T
fun <E:T> addToList(
index: Class<E>,
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
fun addToList(
index: Class<in T>,
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
fun <E> addToList(
index: Class<E>,
value: (E) -> Unit
) where E : T {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
但它永远行不通。有没有办法做到这一点?我无法在 Whosebug 中找到任何有关此场景的答案。
你的方差倒转了。如果你想让你的地图接受 类 的 T 子类型,那么它需要是 <out T>
。如果您不检查密钥,您可能只输入 Class<*>
.
您声明函数的第一种方式是正确的。
abstract class Endpoint<T>(
) {
private val myList: MutableMap<Class<out T>, MutableList<String>> = mutableMapOf()
fun <E : T> addToList(
index: Class<E>,
value: String
) {
myList.getOrPut(index, ::mutableListOf).add(value)
}
}
我正在尝试实现接受通用参数的函数定义,只要它扩展了另一个特定的通用类型。简而言之;参数 A 必须扩展参数 B,其中 A 和 B 都是通用的。
下面是我的示例
abstract class Endpoint<T>(
) {
private val myList: MutableMap<Class<T>, MutableList<((T) -> Unit)>> = mutableMapOf()
fun addToList(
index: Class<E>, <-- E extends T
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
}
用法示例为
部分封印class
sealed class MainSealedClass {
data class ChildClass(val someParam: Int): MainSealedClass()
}
以及函数调用
anEndpointInstance.addToList(MainSealedClass.ChildClass::class.java, "some value")
我希望不必在抽象 class 声明中定义 E,因为 T 已经在那里定义了。
我也尝试过以下操作:
将 myList 定义为接受扩展 T 的键
val myList: MutableMap<Class<in T>, MutableList<String>>
将 E 定义为 T 类型(找不到如何在函数中指定它扩展 T
fun <E:T> addToList(
index: Class<E>,
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
fun addToList(
index: Class<in T>,
value: (E) -> Unit
) {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
fun <E> addToList(
index: Class<E>,
value: (E) -> Unit
) where E : T {
myList[index] = (myList[index] ?: mutableListOf()).apply { add(value) }
}
但它永远行不通。有没有办法做到这一点?我无法在 Whosebug 中找到任何有关此场景的答案。
你的方差倒转了。如果你想让你的地图接受 类 的 T 子类型,那么它需要是 <out T>
。如果您不检查密钥,您可能只输入 Class<*>
.
您声明函数的第一种方式是正确的。
abstract class Endpoint<T>(
) {
private val myList: MutableMap<Class<out T>, MutableList<String>> = mutableMapOf()
fun <E : T> addToList(
index: Class<E>,
value: String
) {
myList.getOrPut(index, ::mutableListOf).add(value)
}
}