首页 > 解决方案 > 具有协方差的交集类型

问题描述

考虑以下内容:

trait AA {
    def children: List[AA]
}

trait BB {
    def children: List[BB]
}

class CC extends AA, BB {
    override def children: List[AA] & List[BB] = ???
}

当我们重写childreninCC时,被重写的方法是顶级方法的合并实体。因此返回类型List[AA] & List[BB]是有意义的。

我不明白的是,下面是如何编译的?

class DD extends AA, BB {
    override def children: List[AA & BB] = ???
}

List 是协变的,因此(这里是proof的来源):

List[AA & BB] <: List[AA] & List[BB]

DD如果也 只能编译List[AA] & List[BB] <: List[AA & BB]。这是真的吗?如果是这样,那么不是List[AA] & List[BB] =:= List[AA & BB]。请建议


在我看来List[AA & BB] =:= List[AA] & List[BB]。考虑一下:

    val xx: List[AA & BB] = ???
    val yy: List[AA] & List[BB] = ???
    
    val z1: List[AA] & List[BB] = xx
    val z2: List[AA & BB] = yy

标签: scalagenericsdottyscala-3

解决方案


您编写的 DD 编译List[AA] & List[BB]必须是List[AA & BB]. 我不明白你为什么这么想,事实上你错了。方法返回类型是协变的,因此反过来:List[AA & BB]必须是List[AA] & List[BB]. 而且确实是这样,所以代码没问题。


推荐阅读