En Scala, nous pouvons utiliser au moins deux méthodes pour la rénovation existants ou de nouveaux types. Supposons que nous voulons exprimer que quelque chose peut être quantifiée à l'aide d'un Int
. On peut définir les traits.
La conversion implicite
trait Quantifiable{ def quantify: Int }
Et ensuite, nous pouvons utiliser les conversions implicites à quantifier, par exemple, les Chaînes et les Listes.
implicit def string2quant(s: String) = new Quantifiable{
def quantify = s.size
}
implicit def list2quantifiable[A](l: List[A]) = new Quantifiable{
val quantify = l.size
}
Après l'importation de ces éléments, nous pouvons appeler la méthode quantify
sur les chaînes et les listes. Notez que le quantifiables liste des magasins de sa longueur, de sorte qu'il évite le cher de la traversée de la liste des appels suivants à l' quantify
.
Les classes de Type
Une alternative est de définir un "témoin" Quantified[A]
que les états, qu'un certain type A
peuvent être quantifiés.
trait Quantified[A] { def quantify(a: A): Int }
Ensuite, nous présentons des exemples de ce type de classe pour String
et List
quelque part.
implicit val stringQuantifiable = new Quantified[String] {
def quantify(s: String) = s.size
}
Et si, ensuite, on écrire une méthode qui a besoin de quantifier ses arguments, nous écrivons:
def sumQuantities[A](as: List[A])(implicit ev: Quantified[A]) =
as.map(ev.quantify).sum
Ou en utilisant le contexte lié à la syntaxe:
def sumQuantities[A: Quantified](as: List[A]) =
as.map(implicitly[Quantified[A]].quantify).sum
Mais quand à l'utilisation de la méthode?
Maintenant vient la question. Comment puis-je décider entre ces deux concepts?
Ce que j'ai remarqué jusqu'à présent.
les classes de type
- type de classes permettent de nice contexte lié syntaxe
- avec les classes de type je n'ai pas de créer un nouvel objet wrapper sur chaque utilisation
- le contexte lié à la syntaxe ne fonctionne plus si le type de la classe a de multiples paramètres de type; imaginez que je veux quantifier les choses, non seulement avec des nombres entiers, mais avec des valeurs d'un type général
T
. Je voudrais créer une classe de typeQuantified[A,T]
la conversion implicite
- depuis que j'ai créer un nouvel objet, je peut mettre en cache les valeurs de y ou de calculer une meilleure représentation; mais dois-je éviter cela, car il peut arriver plusieurs fois et une conversion explicite serait probablement être invoqué qu'une seule fois?
Ce que j'attends d'une réponse
Présenter un (ou de plusieurs) cas d'utilisation(s) où la différence entre les deux concepts, questions et d'expliquer pourquoi je préfère l'un sur l'autre. Également expliquer l'essence des deux concepts et leurs relations les uns aux autres serait bien, même sans exemple.