我有一个这样的课程:
abstract class Foo[I, T, A <: Bar[I, T]](x: SomeClass[A]){
当我想继承类Foo时,我要指定类型T和I,它们可以从类型A的类型参数中提取。(即有足够的数据来提取这些类型。)Scala编译器是否允许以某种方式提取它们?我想写一些类似的东西:
abstract class Foo[A <: Bar[_, _]](x: SomeClass[A]){
type Bar[I, T] = A // <-- something like pattern matching
奇怪的是,我可以写出来,但type Bar[I, T] = A
行似乎没有声明任何内容。该行已通过,但我既不能使用I
类型,也不能使用T
类型。
我可以做类似的事吗?
我知道我可以使用abstract class Foo[I, T](x: SomeClass[A]){
然后定义type A = Bar[I, T]
,但它失去了一些普遍性。另外,这种情况意味着代码用户的更多(样板)代码,因为它们可能为Bar[I, T]
定义了一个快捷方式(即类型别名)。
我可以将抽象类Foo
重写为特征,我可能会这样做。但我不确定它是否有帮助。
答案 0 :(得分:1)
当类型参数变得不合适时,应该尝试使用抽象类型:
scala> class Bar[I, T](i: I, t: T)
defined class Bar
scala> class SomeClass[A](a: A)
defined class SomeClass
scala> trait Trait { type I; type T; type A = Bar[I,T] }
defined trait Trait
scala> class Foo(x: SomeClass[Foo#A]) extends Trait { type I = String; type T = String }
defined class Foo
scala> new Foo(new SomeClass(new Bar("", ""))) // works
res0: Foo = Foo@7e1f613c
scala> new Foo(new SomeClass(new Bar("", 0))) // does not work
<console>:12: error: type mismatch;
found : Int(0)
required: String
new Foo(new SomeClass(new Bar("", 0)))
^