Kotlin:动态类型参数的默认值
Kotlin: Default value for dynamically typed arguments
为什么这是正确的而下面的是错误的?
正确一个
fun main () {
AppModule().provideHttpClient(CIO)
}
错误
fun <T : HttpClientEngineConfig> provideHttpClient(engineFactory: HttpClientEngineFactory<T> = CIO): HttpClient
Type mismatch.
Required:HttpClientEngineFactory
Found: CIO
CIO 定义为:
public object CIO : HttpClientEngineFactory<CIOEngineConfig> {
init {
addToLoader()
}
override fun create(block: CIOEngineConfig.() -> Unit): HttpClientEngine =
CIOEngine(CIOEngineConfig().apply(block))
override fun toString(): String = "CIO"
}
泛型方法的语义是“我可以使用任何类型”,因此泛型方法的类型参数由调用者指定 - 调用者可以决定 T
是什么。因此,对于调用者可能传入的任何 T
,您指定为被调用者的默认值必须与 HttpClientEngineFactory<T>
兼容。
在这里使用 CIO
不起作用,因为您将 T
强制为 CIOEngineConfig
。
想象一下如果允许默认值 CIO
并且调用者这样做会发生什么:
AppModule().provideHttpClient<SomeOtherEngineConfig>()
从声明 provideHttpClient
的方式来看,这应该是可能的 - 我正在为泛型类型参数 T
传递 SomeOtherEngineConfig
,并且由于 engineFactory
参数有默认值,我不需要传递任何其他参数。但是当这实际上得到运行时,CIO
的默认值用于HttpClientEngineFactory<SomeOtherEngineConfig>
!
类型的参数
解决这个问题很容易:只需声明另一个非通用的 provideHttpClient
重载:
fun provideHttpClient(): HttpClient = provideHttpClient(CIO)
为什么这是正确的而下面的是错误的?
正确一个
fun main () {
AppModule().provideHttpClient(CIO)
}
错误
fun <T : HttpClientEngineConfig> provideHttpClient(engineFactory: HttpClientEngineFactory<T> = CIO): HttpClient
Type mismatch.
Required:HttpClientEngineFactory
Found: CIO
CIO 定义为:
public object CIO : HttpClientEngineFactory<CIOEngineConfig> {
init {
addToLoader()
}
override fun create(block: CIOEngineConfig.() -> Unit): HttpClientEngine =
CIOEngine(CIOEngineConfig().apply(block))
override fun toString(): String = "CIO"
}
泛型方法的语义是“我可以使用任何类型”,因此泛型方法的类型参数由调用者指定 - 调用者可以决定 T
是什么。因此,对于调用者可能传入的任何 T
,您指定为被调用者的默认值必须与 HttpClientEngineFactory<T>
兼容。
在这里使用 CIO
不起作用,因为您将 T
强制为 CIOEngineConfig
。
想象一下如果允许默认值 CIO
并且调用者这样做会发生什么:
AppModule().provideHttpClient<SomeOtherEngineConfig>()
从声明 provideHttpClient
的方式来看,这应该是可能的 - 我正在为泛型类型参数 T
传递 SomeOtherEngineConfig
,并且由于 engineFactory
参数有默认值,我不需要传递任何其他参数。但是当这实际上得到运行时,CIO
的默认值用于HttpClientEngineFactory<SomeOtherEngineConfig>
!
解决这个问题很容易:只需声明另一个非通用的 provideHttpClient
重载:
fun provideHttpClient(): HttpClient = provideHttpClient(CIO)