| Source: | https://subversion.assembla.com/svn/saintamh/lib-js/trunk/saintamh/iterator.js |
|---|---|
| Source (en couleurs): | https://www.assembla.com/code/saintamh/subversion/nodes/lib-js/trunk/saintamh/iterator.js |
Cette librairie vise à donner au programmeur JavaScript un outil
ressemblant à la classe Seq de Scala, ou aux iterators de Python.
La librarie crée un symbole, I, qui est placé dans le namespace global.
Traité comme une fonction, I sert à créer un itérateur à partir de tout objet
itérable:
var i0 = I([1,2,3]); // à partir d'un Array
var i1 = I("A bright cold day in April"); // à partir d'une String
var i2 = I(document.getElementsByTagName('a')); // à partir d'un "array-like"
La librairie fournit aussi plusieurs utilitaires pour créer divers types d'itérateurs:
// i3 contient toutes les substrings qui matchent
var i3 = I.matches (/\w+/, "Ipsum lorem dolor sit amet");
// I.split(re,str) est équivalent à I(str.split(re))
var i4 = I.split (/\s+/, "Ipsum lorem dolor sit amet");
// Itérateurs sur les clés, les valeurs, ou les paires clé/valeur d'un objet:
var i5 = I.keys ({a: 1, b: 2});
var i6 = I.values ({a: 1, b: 2});
var i7 = I.items ({a: 1, b: 2});
// Un énumérateur d'entiers. Comme tous les autres itérateurs de cette
// librarie, l'évaluation se fait de manière paresseuse, c'est-à-dire que
// la liste complète d'entiers n'est pas toute contenue en mémoire en même
// temps.
var i8 = I.range (0, 1000*1000);
// Concaténation d'itérables
var i9 = I.chain (i0, [4,5,6], '789');
Tous les itérateurs ont la même interface. La fonctionalité de base tient
en deux méthodes, qui ont les mêmes noms que leurs cousins chez
java.util.Iterator:
hasNext() retourne un booléen indiquant si l'itérateur a
d'autres valeurs à retourner;next()
retourne la prochaine valeur, et avance l'itérateur d'un élément.L'utilisateur de la librairie n'a pas normalement à invoquer ces méthodes directement -- il utilise plutôt les méthodes ci-dessous:
Les itérateurs offrent plusieurs méthodes qui permettent de les manipuler et de les transformer:
// `foreach` permet d'itérer sur le contenu d'un Array sans avoir à
// en manipuler les indices
I(anyArray).foreach (function (elem) {
doSomethingWith(elem);
});
// retourne "0-1-4-64-81"
I.range(10).
map (function (n) { return n*n }).
grep (function (n) { return n%10 < 5 }).
join ('-');
// S'il vous prenait l'envie de ré-implémenter les opérateurs booléens:
function AND () {
return I(arguments).
map (I.nvoke()).
all();
}
// Notez que la définition qui précède s'arrête au premier élément qui est
// faux, comme l'opérateur &&. Par exemple, ce code retourne `false` sans
// jamais invoquer la deuxième fonction:
AND (
function () { return false; },
function () { throw "Huh?"; }
);
Chacune des méthodes qui prend en argument une fonction possède aussi une seconde version, faite pour les itérateurs qui eux-mêmes contiennent des itérables. Cette version appelle la fonction qui lui est donnée pour chaque élément dans l'itérateur, avec les sous-éléments comme arguments à la fonction (tsé veux dire...):
// Itération sur le contenu d'un Array, avec les indices
I(anyArray).enumerate().foreach$ (function (i, elem) {
print ("Elem at position " + i + " is " + elem);
});
Il y a plusieurs autres méthodes disponibles, le mieux est de voir le code source, ou le fichier de unit tests, qui est à peu près lisible.