2009-02-23 20 views
7

Me preguntaba: ¿puedo descomponer un tipo de tupla en los tipos de sus componentes en Scala?Desempaquetar tipos de tuplas en Scala

quiero decir, algo como esto

trait Container { 
    type Element 
} 

trait AssociativeContainer extends Container { 
    type Element <: (Unit, Unit) 
    def get(x : Element#First) : Element#Second 
} 

Respuesta

3

No se puede descomprimir, por sí mismo, pero tal vez con ello se consigue lo que quiere:

type First 
    type Second 
    type Element = (First, Second) 
    def get(x: First): Second 
+0

Eso es lo que pensaba que tenía que hacer, pero quería evitar, porque eso sería cambiar la implementación de las clases que se extienden este rasgo. – jpalecek

+0

Además, ¿significa esto que el par de elementos sería el mismo par incluso en subclases? ¿No debería ser más bien Elemento <: (Primero, Segundo) [o quizás también limitado?] – jpalecek

0

estoy un poco tarde para esto, pero ¿qué pasa con el uso de patrones de coincidencia? No tiene absolutamente el tipo de devolución correcta, y mi sintaxis podría ser un poco apagado, pero aquí va:

def get[K](key: K): Iterable[Any] { 
    for ((key, x) <- elements) yield x 
} 
3

Esto no desempaquetar los tipos, pero no limitan los tipos A y B al llamar get .

trait Container { 
    type Element 
} 

trait AssociativeContainer extends Container { 
    type Element <: Tuple2[_, _] 

    def get[A, B](x: A)(implicit ev: (A, B) =:= Element): B 
} 

Esto parece prometedor, pero está engañando - no funciona si Element es abstracto.

def Unpack[T<:Tuple2[_, _]] = new { 
    def apply[A, B](implicit ev: T <:< (A, B)) = new { 
    type AA = A 
    type BB = B 
    } 
} 

trait AssociativeContainer { 
    type Element = (Int, String) 
    val unpacked = Unpack[Element].apply 
    type A = unpacked.AA 
    type B = unpacked.BB 

    1: A 
    "": B 
    def get(x: A): B 
} 
Cuestiones relacionadas