- Comment comparer des tableaux en JavaScript ? (5 réponses )
Réponses
Trop de publicités?Option 1
L'option la plus simple, fonctionne dans presque tous les cas, sauf qu' null
!==undefined
mais ils sont tous les deux convertis à la représentation JSON null
et considérées comme égales:
function arraysEqual(a1,a2) {
return JSON.stringify(a1)==JSON.stringify(a2);
}
Fonctionne même si votre tableau contient des objets! Normalement, ({1:2}) != ({1:2})
, mais cette méthode considèrent comme des égaux, de sorte que l'arbitraire des expressions comme arrayEquals([{1:[]},2], [{1:[]},2])
fonctionne, même (si vous le permettez) arrayEquals(1,2)
ou arrayEquals({1:2},{1:2})
.
(Si cela fonctionne encore avec des objets dépend de l'implémentation JSON sortes de clés, cependant. Le JSON de {1:2,3:4}
peut ou peut ne pas être égale à {3:4,1:2}
et, en fonction de la mise en œuvre. Il semble au moins travailler dans Chrome. Si vous choisissez de ne pas utiliser des objets dans vos listes, cela devrait fonctionner correctement.)
Option 2
Plus "propre", qui travaille avec des tableaux imbriqués (et que vous pouvez remplacer pour traiter des cas particuliers, comme des objets ordinaires et nulle/non défini et des objets personnalisés, si vous le désirez):
// generally useful functions
function type(x) {
// e.g. type(/asdf/g) --> "[object RegExp]"
return Object.prototype.toString.call(x);
}
function zip(arrays) {
// e.g. zip([[1,2,3],[4,5,6]]) --> [[1,4],[2,5],[3,6]]
return arrays[0].map(function(_,i){
return arrays.map(function(array){return array[i]})
});
}
// helper functions
function allCompareEqual(array) {
// e.g. allCompareEqual([2,2,2,2]) --> true
// does not work with nested arrays or objects
return array.every(function(x){return x==array[0]});
}
function isArray(x){ return type(x)==type([]) }
function getLength(x){ return x.length }
function allTrue(array){ return array.reduce(function(a,b){return a&&b},true) }
// e.g. allTrue([true,true,true,true]) --> true
// or just array.every(function(x){return x});
function allDeepEqual(things) {
// works with nested arrays
if( things.every(isArray) )
return allCompareEqual(things.map(getLength)) // all arrays of same length
&& allTrue(zip(things).map(allDeepEqual)); // elements recursively equal
//else if( this.every(isObject) )
// return {all have exactly same keys, and for
// each key k, allDeepEqual([o1[k],o2[k],...])}
// e.g. ... && allTrue(objectZip(objects).map(allDeepEqual))
//else if( ... )
// extend some more
else
return allCompareEqual(things);
}
Démo:
allDeepEqual([ [], [], [] ])
true
allDeepEqual([ [1], [1], [1] ])
true
allDeepEqual([ [1,2], [1,2] ])
true
allDeepEqual([ [[1,2],[3]], [[1,2],[3]] ])
true
allDeepEqual([ [1,2,3], [1,2,3,4] ])
false
allDeepEqual([ [[1,2],[3]], [[1,2],[],3] ])
false
allDeepEqual([ [[1,2],[3]], [[1],[2,3]] ])
false
allDeepEqual([ [[1,2],3], [1,[2,3]] ])
false
Pour l'utiliser comme une fonction régulière, faire:
function allDeepEqual2() {
return allDeepEqual([].slice.call(arguments));
}
Démo:
allDeepEqual2([[1,2],3], [[1,2],3])
true
jQuery n’a pas une méthode de comparaison des baies. Toutefois, la bibliothèque de souligner a une telle méthode : isEqualet il peuvent traiter une variété d’autres cas (comme objet littéraux) aussi bien. S’en tenir à l’exemple fourni :
Soit dit en passant : trait de soulignement a beaucoup d’autres méthodes que jQuery est manquant, donc c’est un excellent complément à jQuery.
Il existe plusieurs prototypes bibliothèques là-bas qui prennent la peine de la fonctionnalité de tableau.
Essayez celui-ci pour de nombreuses fonctions courantes du tableau :
http://www.svendtofte.com/code/usefull_prototypes/
Après avoir inclus le script, vous serez en mesure d’appeler ce qui suit :