You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Kotlin:为List<Any>添加泛型时的类型不匹配问题

解决泛型列表拼接的类型不匹配问题

先看你的代码场景:
你定义了一个泛型数据类:

data class MyObject<T>(
    val entity: T
)

尝试拼接两个不同泛型参数的MyObject列表:

fun concatLists(): List<MyObject<Any>> {
    val listOfAs = listOf(MyObject<A>())
    val listOfBs = listOf(MyObject<B>())

    return mutableListOf<MyObject<Any>>().also {
                it.addAll(listOfAs)
                it.addAll(listOfBs)
            }
}

但遇到了类型不匹配错误:

Type mismatch.
Required:
Collection<MyObject<Any>>
Found:
List<MyObject<A>>

错误原因

你混淆了泛型的不变性和普通类的继承关系。Kotlin中泛型默认是不变的:哪怕A是Any的子类,MyObject<A>也不是MyObject<Any>的子类,两者之间没有继承关系。虽然List是Collection的子类,但泛型参数的不兼容性导致整个集合类型不匹配。

解决方案

有两种常用的解决方式:

1. 让MyObject支持协变

因为你的MyObject只有只读的val entity,属于生产型泛型(只向外暴露T类型的值,不接收T类型的输入),可以给泛型参数加上out关键字开启协变:

data class MyObject<out T>(
    val entity: T
)

开启协变后,MyObject<A>会被视为MyObject<Any>的子类型,此时你的原代码就能正常编译运行——因为List<MyObject<A>>可以适配Collection<MyObject<Any>>的要求。

2. 不修改MyObject,强制类型转换

如果无法修改MyObject的定义,可以通过类型转换让列表适配目标类型:

fun concatLists(): List<MyObject<Any>> {
    val listOfAs = listOf(MyObject<A>())
    val listOfBs = listOf(MyObject<B>())

    return mutableListOf<MyObject<Any>>().also {
        it.addAll(listOfAs as List<MyObject<Any>>)
        it.addAll(listOfBs as List<MyObject<Any>>)
    }
}

或者更简洁的写法:

fun concatLists(): List<MyObject<Any>> {
    val listOfAs = listOf(MyObject<A>())
    val listOfBs = listOf(MyObject<B>())
    return (listOfAs + listOfBs) as List<MyObject<Any>>
}

注意:这种方式需要确保类型安全,因为如果MyObject后续添加了可写的T类型属性,强制转换可能导致运行时错误,但在当前只读的场景下是安全的。

内容的提问来源于stack exchange,提问作者Henry Williams

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.04 22:12:20