Je voudrais appeler « contient » sur mes Iterables :-)Pourquoi Iterator a-t-il une méthode contains mais pas Iterable, dans Scala 2.8?
Répondre
la raison Iterable
n'a pas une méthode contains
est parce que la façon dont il est défini peut avoir des conséquences directes sur vari ance. Fondamentalement, il existe deux signatures de type qui ont du sens pour cela:
def contains(v: Any): Boolean
def contains(v: A): Boolean
La seconde définition a augmenté la sécurité de type. Cependant, A
, qui est le paramètre de type de collection, apparaît dans une position à contre-sens, ce qui force la collection à être invariante. Il pourrait être définie comme ceci:
def contains[B >: A](v: B): Boolean
mais qui n'offrirait une amélioration par rapport à la première signature, en utilisant Any
. En conséquence, immutable.Seq
est co-variant et utilise la première signature, tandis que immutable.Set
est invariant et utilise la deuxième signature.
Je ne sais pas pourquoi contains
n'est pas défini sur Iterable
ou TraversableOnce
, mais vous pouvez facilement définir vous-même:
class TraversableWithContains[A](underlying: TraversableOnce[A]) {
def contains(v: Any): Boolean =
underlying.exists(_ == v)
}
implicit def addContains[A](i: Iterable[A]) = new TraversableWithContains(i)
et l'utiliser comme si elle était définie sur Iterable:
val iterable: Iterable[Int] = 1 to 4
assert(iterable.contains(3))
assert(!iterable.contains(5))
Remarque: 'contains' ** est ** implémenté en utilisant la signature' contains [A1>: A] (elem: A1) 'dans' SeqLike' (au moins dans Scala 2.11.8). Je ne pense pas que ce soit le même que d'utiliser 'Any' - il place des contraintes sur le type' B' - vous pouvez passer 'Any', mais vous ne pouvez pas passer un type qui est connu pour être non apparenté. – Suma
@Suma Bien sûr, vous pouvez. Allez-y et essayez. Si vous passez un type non apparenté, 'A1' sera supposé être le supertype commun. Et parce que tout est descendant de 'Any', alors tous les types ont un supertype commun entre eux. –
Vous avez raison. Y a-t-il une raison pour laquelle la signature dans la bibliothèque est telle qu'elle est, et non avec Any, comme vous écrivez, alors? – Suma