简体   繁体   English

Scala-协变类型层次结构的根

[英]Scala - root of covariant type hierarchy

The following Scala class: 以下Scala类:

class Foo[+T <: Bar] extends FooBase ...

effectively defines a type hierarchy which has Foo[Bar] as its root - ie any valid Foo[X] will be assignable to a Foo[Bar] value or variable: 有效地定义了以Foo [Bar]为根的类型层次结构-即,任何有效的Foo [X]都可以分配给Foo [Bar]值或变量:

val v1: Foo[Bar] = new Foo[SubBar1]();
val v2: Foo[Bar] = new Foo[SubBar2]();

FooBase is further up and could also imply objects that are not Foo - the following shows the issue: FooBase更远,也可能暗示不是Foo的对象-以下显示了问题:

class Trouble extends FooBase ...
val iOnlyWantFooHere: FooBase = new Trouble();

... and also FooBase is not aware of type T, so its members cannot specify it and I'd have to override these definitions in Foo to specialize them: ...而且FooBase也不知道类型T,因此它的成员无法指定它,我必须重写Foo中的这些定义以使其专业化:

class FooBase {
  def ohNoIDontKnowTheType: Bar;
}

class Foo[+T <: Bar] extends FooBase {
  override def ohNoIDontKnowTheType: T = ...;
}

There are other ways to work around that issue, but the point should be clear. 还有其他方法可以解决该问题,但是要点很明确。

Finally, my actual question is what is the root of the following hierarchy: 最后,我的实际问题是以下层次结构的根源是什么:

class Foo[+T <: Foo[T]] extends FooBase ...

Again, do not tell me FooBase, because that is not the case. 同样,不要告诉我FooBase,因为事实并非如此。 Yes, I could insert another class in between specifically for the purpose, but that is still not a true answer as indicated above. 是的,我可以为此专门在两者之间插入另一个类,但这仍然不是如上所述的正确答案。

Scala does not like just Foo (without the type parameter), and it is not Foo[_] either as then accessing methods returning the value of the type parameter type will actually be Any , not Foo . Scala不仅仅喜欢Foo (没有type参数),也不是Foo[_] ,因为返回类型参数type值的访问方法实际上将是Any ,而不是Foo Of course, we cannot do Foo[Foo] either since that is also missing the type parameter for the second one and Foo[Foo[_]] or Foo[Foo[Foo[Foo[_]]] only gets us so many levels. 当然,我们也不能执行Foo[Foo] ,因为它也缺少第二个参数的类型参数,而Foo[Foo[_]]Foo[Foo[Foo[Foo[_]]]只能给我们提供很多层次。

Is there an answer at all or does Scala lack support for this? 根本没有答案吗?还是Scala对此缺乏支持?

Thanks in advance! 提前致谢!

How about Foo[_ <: Foo[_]] ? Foo[_ <: Foo[_]]怎么样? Which, by the way, I did mention in my answer to your other question. 顺便说一句,我在回答其他问题时确实提到了这一点。 Or you could write it like this: 或者您可以这样写:

type Base = Foo[t] forSome { type t <: Foo[t] }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM