在Java中,你可以编写像这样的方法,它不会抛出任何强制转换警告,并根据返回类型推断出类型:
public static <T> T getService(final String name) {
return (T) appCtx.getBean(name);
}
以下是一些使用示例:
public static StatusService getStatusService() {
return getService("statusService");
}
public static VenueService getVenueService() {
return getService("venueService");
}
现在我尝试将其转换为Kotlin并想出了这个:
fun <T> getService(name: String): T {
return appCtx?.getBean(name) as T
}
但是我在这里得到了警告:
Unchecked cast: Any? to T
好的,在浏览Stackoverflow之后我发现你可以用注释将其关闭:
@Suppress("UNCHECKED_CAST")
我不确定这是一个干净的解决方案。
我的问题是:当您通过Kotlin中的返回类型推断出类型时,有没有办法避免这种未经检查的类型转换警告?如果是这样,你怎么能这样做。
更新1
在一些答案和评论(https://stackoverflow.com/a/49918740/2735286和Marko Topolnics&#39;评论)之后,我将代码更改为:
inline fun <reified T> getService(name: String): T {
requireNotNull(appCtx) { "Application context has not been set." }
return appCtx?.getBean(name) as T
}
此代码消除了未经检查的强制转换警告,并提供了改进的错误处理。
更新2
在Alexey Romanov的建议之后,我删除了requireNotNull
并将代码更改为:
var appCtx: ApplicationContext by Delegates.notNull()
private inline fun <reified T> getService(name: String): T {
return appCtx.getBean(name) as T
}
答案 0 :(得分:3)
实际上即使是java编译器(至少从JDK 8u131开始)也会发出类似的警告。所以kotlinc遵循相同的道路。
答案 1 :(得分:2)
这就是演员未经检查的原因,而Kotlin的警告是正确的:
// Java
Object service = <StatusService> getService("venueService");
你会注意到它编译并且在执行时不会抛出异常。这是因为类型擦除将(T) appCtx.getBean(name)
转换为(Object) appCtx.getBean(name)
,这种转换显然总是成功。
reified T
不会发生这种情况,因为在调用网站上已知T
,因此会检查其中的广告。