11
votes

Le modèle de classe de type dans Scala ne considère pas l'héritage?

Je concevons une API en utilisant des classes de type dans certains cas, mais j'ai rencontré un problème de résolution implicite. Comme indiqué ci-dessous, s'il existe un objet implicite pour le type A mais un objet de type B étend un est transmis à la méthode, un objet implicite ne peut pas être trouvé. Existe-t-il un moyen de faire ce travail ou de faire des appelants doit mettre des objets implicites dans la portée de chaque sous-classe?

Voici un exemple: xxx

Ceci ne compile pas à compiler avec La sortie suivante: xxx


1 commentaires

J'ai aussi essayé de modifier la définition de l'appel à: DEF appelez [x, x2 <: x] (x: x2) (implicite x2: t [x]) = println (x) et qui n'a pas aidé


3 Réponses :


2
votes

Essayez ceci: xxx

ou simplement: xxx


0 commentaires

4
votes

Les travaux suivants finissent bien:

scala> def call[X](x: X)(implicit evidence: T[X]<:<T[X])  = println(x)
call: [X](x: X)(implicit evidence: <:<[T[X],T[X]])Unit

scala> call(new A)
line0$object$$iw$$iw$A@1d869b2

scala> call(new B)
line2$object$$iw$$iw$B@b3a5d1

scala> val b = new B
b: B = B@30e4a7

scala> call(b)
line2$object$$iw$$iw$B@30e4a7


6 commentaires

Existe-t-il un moyen de recevoir une preuve 1 $? Supposons par exemple que T était une fonction et X était le paramètre. Je ne peux pas appeler des preuves (x)


Pourquoi ne peux-tu pas? Vous pouvez l'appeler par nom preuves 1 $ , comme tout autre paramètre [implicit].


Si vous avez plusieurs paramètres de type sur la méthode, il y aura des preuves 1 $, la preuve 2 etc: [x, z] (x: x) (preuve implicite 1: T [x], preuve implicite 2: T [Z ]) Unité


Ma question n'a pas tout à fait capturé mes besoins. J'ai adoré apprendre ce conseil, mais mes besoins réels avaient été: Trait T [x] étend la fonction1 [x, booléen] . et appeler est: def appel [x] (x: x) (implicite x2: t [x]) = x2 (x) . S'est avéré avec t [-x] travaillé pour moi. Cool pour en savoir plus sur le <:


def foo [A: M] = {Valma = implicitement [m [a]; ...}


@ Jesse-eicha si t [-x] a travaillé pour vous, pourquoi ne pas accepter la réponse que j'ai fournie?



8
votes

L'appel appel (nouveau b) signifie appel [b] (nouveau b) (tb) tel que la tuberculose est de type T [B] ou sous-classe de celui-ci. . (Une méthode qui s'attend à ce que l'argument de type T ne puisse s'attendre qu'aucune touche T ou sous-classe de T, par exemple, def FOO (S: String) ne peut pas être appelé avec argument de type tout ) . T [a] n'est pas un sous-type de t [b]

Pour corriger, vous pouvez changer T pour définir t [-x] . Cela signifie que le compilateur considérera t [a] être un sous-type de T [B]


2 commentaires

Le problème est, même si vous définissez également objet implicity tb étend à [b] , implicitement [t [b]] == t.ta . Lamsvn.epfl.ch/trac/scala/ticket/2509


Cela semble raisonnable, car la TA est alors plus spécifique que la tuberculose et la TA est-une tuberculose afin de pouvoir être utilisable où T [B] est. Si vous voulez que l'implicite correspond au type exactement, définissez t comme t [x]