Angenommen, ich habe zwei Klassen A und B, mit B ein Subtyp von A. Dies ist offensichtlich nur Teil einer reicheren Typhierarchie, aber ich denke nicht, dass das relevant ist. Angenommen, A ist der Stamm der Hierarchie. Es gibt eine Erfassungsklasse C, die eine Liste von As verfolgt. Allerdings möchte ich C generisch machen, so dass es möglich ist, eine Instanz zu erstellen, die nur Bs behält und keine A akzeptiert.Generics in einer bidirektionalen Assoziation
class A(val c: C[A]) {
c.addEntry(this)
}
class B(c: C[A]) extends A(c)
class C[T <: A]{
val entries = new ArrayBuffer[T]()
def addEntry(e: T) { entries += e }
}
object Generic {
def main(args : Array[String]) {
val c = new C[B]()
new B(c)
}
}
Der obige Code offensichtlich den Fehler geben 'Typ Mismatch: gefunden C [B] erforderlich C [A]' auf der Linie new B(c)
.
Ich bin mir nicht sicher, wie das behoben werden kann. Es ist nicht möglich, C in T kovariant zu machen (wie C[+T <: A]
), weil der ArrayBuffer in T nichtvariabel typisiert ist. Es ist nicht möglich, den Konstruktor von B ein C [B] zu verlangen, weil C nicht kovariant sein kann.
Banne ich hier den falschen Baum? Ich bin ein kompletter Scala-Neuling, also können Ideen und Tipps hilfreich sein. Vielen Dank!
EDIT: Im Grunde, was ich möchte ist haben, dass der Compiler akzeptiert sowohl
val c = new C[B]()
new B(c)
und
val c = new C[A]()
new B(c)
aber ablehnen würden
val c = new C[B]()
new A(c)
Es ist wahrscheinlich möglich um die Typisierung des ArrayBuffers in C zu entspannen, um A statt T zu sein, und somit in der addEntry-Methode auch, wenn das hilft.
Es ist in der Tat falsch für genau die Gründe, die Sie hier beschreiben, wenn C kovariant ist, aber das ist nicht unbedingt eine Voraussetzung. Ich glaube nicht, dass es notwendig ist, C [B] zu einem Subtyp von C [A] zu machen. – Verhoevenv
@Verhoevenv Wenn 'C [B]' kein Untertyp von 'C [A]' war, wie können Sie erwarten, dass 'new B (c)' funktioniert, wenn 'c' vom Typ' C [B] 'ist ? Ich sehe gerade nach Ihrer Revision und Sie verlangen etwas Unmögliches. –