0x7、Kotlin中的型变
和Java泛型一样,Kotlin中的泛型也是「
不变的
」,没有「
通配符类型
」,但有两个其他的东西:「
声明处型变
」(declaration-site variance) 与 「
类型投影
」(type projections)
① 声明处型变
其实就是用「
out
」和「
in
」关键字来替换
-
「
out
」
协变
,等同于Java中的<? extends>,
能读不能写
,代码示例如下:
-
「
in
」
逆变
,等同于Java中的<? super>,
能写不能读
,代码示例如下:
② 类型投影
其实就是对应Java中的*通配符:
-
Java中<?>等同于<* extends Object>
0x7、Kotlin获取泛型类型
在Kotlin中可以通过下述四种方法获取泛型的类型(前两种Java也适用):
① 匿名内部类
原理:
匿名内部类的声明在编译时进行,实例化在运行时进行
。
代码示例如下
:
② 反射
获取运行时泛型参数类型
,子类可获得父类泛型的具体类型。
代码示例如下
:
③ 实例化类型参数代替类引用
定义一个扩展函数用于启动Activity,代码示例如下:
fun <T: Activity> FragmentActivity.startActivity(context: Context, clazz: Class<T>) {
startActivity(Intent(context, clazz))
// 调用
startActivity(context, MainActivity::class.java)
④ 内联函数
Kotlin中使用「
inline
」关键字定义一个内联函数,配合「
reified
」具体化(类型不擦除),得到使用泛型类型的Class。修改后的代码示例如下:
inline fun <reified T : Activity> Activity.startActivity(context: Context) {
startActivity(Intent(context, T::class.java))
// 调用
startActivity<MainActivity>(context)
参考文献:
什么?泛型本身也可以是nullable?上来就抛这么个问题实在是不够友好~
首先回顾,什么是泛型?[Oracle Java Tutorials](https://docs.oracle.com/javase/tutorial/extra/generics/index.html)
> Introduced in J2SE 5.0, this long-awaited enhancemen