web-dev-qa-db-fra.com

Comment puis-je vérifier si le tableau d'objets a des valeurs de propriété en double?

J'ai besoin d'aide pour parcourir le tableau, je reste bloqué ou je réinvente la roue.

values = [
    { name: 'someName1' },
    { name: 'someName2' },
    { name: 'someName1' },
    { name: 'someName1' }
]

Comment puis-je vérifier s'il y a deux (ou plus) valeurs de même nom dans array? Je n'ai pas besoin d'un compteur, il suffit de définir une variable si les valeurs de tableau ne sont pas uniques. N'oubliez pas que la longueur du tableau est dynamique, ainsi que les valeurs du tableau.

40
be-codified

Utilisez array.prototype.map et array.prototype.some :

var values = [
    { name: 'someName1' },
    { name: 'someName2' },
    { name: 'someName4' },
    { name: 'someName2' }
];

var valueArr = values.map(function(item){ return item.name });
var isDuplicate = valueArr.some(function(item, idx){ 
    return valueArr.indexOf(item) != idx 
});
console.log(isDuplicate);

JSFIDDLE.

54
Amir Popovich

Version 6 du script ECMA

Si vous êtes dans un environnement prenant en charge le Set de ECMA Script 6, vous pouvez alors utiliser Array.prototype.some et un objet Set, comme ceci

let seen = new Set();
var hasDuplicates = values.some(function(currentObject) {
    return seen.size === seen.add(currentObject.name).size;
});

Ici, nous insérons chaque objet de name dans le Set et nous vérifions si les size avant et après l'ajout sont identiques. Cela fonctionne parce que Set.size renvoie un nombre basé sur des données uniques (le jeu ajoute uniquement des entrées si les données sont uniques). Si/quand vous avez des noms en double, la taille n'augmentera pas (car les données ne seront pas uniques), ce qui signifie que nous aurions déjà vu le nom actuel et qu'il renverra la valeur true.


ECMA Script 5 Version

Si vous n'avez pas le support de Set, vous pouvez alors utiliser un objet JavaScript normal, comme ceci

var seen = {};
var hasDuplicates = values.some(function(currentObject) {

    if (seen.hasOwnProperty(currentObject.name)) {
        // Current name is already seen
        return true;
    }

    // Current name is being seen for the first time
    return (seen[currentObject.name] = false);
});

La même chose peut être écrite succinctement, comme ceci

var seen = {};
var hasDuplicates = values.some(function (currentObject) {
    return seen.hasOwnProperty(currentObject.name)
        || (seen[currentObject.name] = false);
});

Remarque: Dans les deux cas, nous utilisons Array.prototype.some parce qu'il va court-circuiter. Dès que la fonction obtiendra une valeur de vérité, elle retournera true immédiatement, elle ne traitera pas le reste des éléments.

37
thefourtheye

Pour savoir si un tableau simple a des doublons, nous pouvons comparer les premiers et derniers indices de la même valeur:

La fonction:

var hasDupsSimple = function(array) {

    return array.some(function(value) {                            // .some will break as soon as duplicate found (no need to itterate over all array)
       return array.indexOf(value) !== array.lastIndexOf(value);   // comparing first and last indexes of the same value
    })
}

Tests:

hasDupsSimple([1,2,3,4,2,7])
// => true

hasDupsSimple([1,2,3,4,8,7])
// => false

hasDupsSimple([1,"hello",3,"bye","hello",7])
// => true

Pour un tableau d'objets, nous devons d'abord convertir les valeurs des objets en un tableau simple:

Conversion d'un tableau d'objets en un tableau simple avec map:

var hasDupsObjects = function(array) {

  return array.map(function(value) {
    return value.suit + value.rank

  }).some(function(value, index, array) { 
       return array.indexOf(value) !== array.lastIndexOf(value);  
     })
}

Tests:

var cardHand = [
  { "suit":"spades", "rank":"ten" },
  { "suit":"diamonds", "rank":"ace" },
  { "suit":"hearts", "rank":"ten" },
  { "suit":"clubs", "rank":"two" },
  { "suit":"spades", "rank":"three" },
]

hasDupsObjects(cardHand);
// => false

var cardHand2 = [
  { "suit":"spades", "rank":"ten" },
  { "suit":"diamonds", "rank":"ace" },
  { "suit":"hearts", "rank":"ten" },
  { "suit":"clubs", "rank":"two" },
  { "suit":"spades", "rank":"ten" },
]

hasDupsObjects(cardHand2);
// => true
2
Systems Rebooter

Essayez une simple boucle:

var repeat = [], tmp, i = 0;

while(i < values.length){
  repeat.indexOf(tmp = values[i++].name) > -1 ? values.pop(i--) : repeat.Push(tmp)
}

Démo

si vous recherchez un booléen, le moyen le plus rapide serait

var values = [
    { name: 'someName1' },
    { name: 'someName2' },
    { name: 'someName1' },
    { name: 'someName1' }
]

// solution
var hasDuplicate = false;
values.map(v => v.name).sort().sort((a, b) => {
  if (a === b) hasDuplicate = true
})
console.log('hasDuplicate', hasDuplicate)
2
user2167582

Vous pouvez utiliser map pour ne renvoyer que le nom, puis utiliser cette astuce forEach pour vérifier s’il existe au moins deux fois:

var areAnyDuplicates = false;

values.map(function(obj) {
    return obj.name;
}).forEach(function (element, index, arr) {
    if (arr.indexOf(element) !== index) {
        areAnyDuplicates = true;
    }
});

violon

1
Omri Aharon

With Underscore.js Quelques méthodes avec Underscore peuvent être utilisées. Voici l'un d'entre eux. Vérifier si le tableau est déjà unique.

function isNameUnique(values){
    return _.uniq(values, function(v){ return v.name }).length == values.length
}

With Vanilla JavaScript En vérifiant s'il n'y a pas de noms récurrents dans le tableau.

function isNameUnique(values){
    var names = values.map(function(v){ return v.name });
    return !names.some(function(v){ 
        return names.filter(function(w){ return w==v }).length>1 
    });
}
1
TaoPR
//checking duplicate elements in an array
var arr=[1,3,4,6,8,9,1,3,4,7];
var hp=new Map();
console.log(arr.sort());
var freq=0;
for(var i=1;i<arr.length;i++){
// console.log(arr[i-1]+" "+arr[i]);
if(arr[i]==arr[i-1]){
freq++;

}
else{
hp.set(arr[i-1],freq+1);
freq=0;
}
}
console.log(hp);
1
ravi