Получить все неуникальные значения (т.е. дубликаты / более одного вхождения) в массиве - PullRequest
370 голосов
/ 08 мая 2009

Мне нужно проверить массив JavaScript, чтобы увидеть, есть ли какие-либо повторяющиеся значения. Какой самый простой способ сделать это? Мне просто нужно выяснить, что такое дублированные значения - мне не нужны их индексы или сколько раз они дублируются.

Я знаю, что могу перебрать массив и проверить все остальные значения на совпадение, но, похоже, должен быть более простой способ. Есть идеи? Спасибо!

Подобный вопрос:

Ответы [ 73 ]

3 голосов
/ 02 мая 2013

Вот очень легкий и простой способ:

var codes = dc_1.split(',');
var i = codes.length;
while (i--) {
  if (codes.indexOf(codes[i]) != i) {
    codes.splice(i,1);
  }
}
3 голосов
/ 04 сентября 2016

ES6 предлагает структуру данных Set, которая в основном представляет собой массив, который не принимает дубликаты. С помощью структуры данных Set очень легко найти дубликаты в массиве (используя только один цикл).

Вот мой код

function findDuplicate(arr) {
var set = new Set();
var duplicates = new Set();
  for (let i = 0; i< arr.length; i++) {
     var size = set.size;
     set.add(arr[i]);
     if (set.size === size) {
         duplicates.add(arr[i]);
     }
  }
 return duplicates;
}
3 голосов
/ 30 июля 2017

Я только что нашел простой способ добиться этого, используя фильтр массива

    var list = [9, 9, 111, 2, 3, 4, 4, 5, 7];
    
    // Filter 1: to find all duplicates elements
    var duplicates = list.filter(function(value,index,self) {
       return self.indexOf(value) !== self.lastIndexOf(value) && self.indexOf(value) === index;
    });
    
    console.log(duplicates);
3 голосов
/ 27 апреля 2018

Следовать логике будет проще и быстрее

// @Param:data:Array that is the source 
// @Return : Array that have the duplicate entries
findDuplicates(data: Array<any>): Array<any> {
        return Array.from(new Set(data)).filter((value) => data.indexOf(value) !== data.lastIndexOf(value));
      }

Преимущества:

  1. Одна строка: -P
  2. Вся встроенная структура данных, помогающая повысить эффективность
  3. Быстрее

Описание логики:

  1. Преобразование в набор для удаления всех дубликатов
  2. Итерация по установленным значениям
  3. При каждой проверке заданного значения в исходном массиве на условие «первый индекс значений не равен последнему индексу» ==> Затем выводится как дубликат, иначе он «уникальный»

Примечание: методы map () и filter () эффективны и быстрее.

2 голосов
/ 31 июля 2012

Только для ES5 (т. Е. Ему необходим фильтр polyfill для IE8 и ниже):

var arrayToFilter = [ 4, 5, 5, 5, 2, 1, 3, 1, 1, 2, 1, 3 ];

arrayToFilter.
    sort().
    filter( function(me,i,arr){
       return (i===0) || ( me !== arr[i-1] );
    });
2 голосов
/ 26 мая 2014

Мне не понравилось большинство ответов.

Почему? Слишком сложный, слишком много кода, неэффективный код и многие не отвечают на вопрос о том, чтобы найти дубликаты (а не дать массив без дубликатов).

Следующая функция возвращает все дубликаты:

function GetDuplicates(arr) {
  var i, out=[], obj={};
  for (i=0; i < arr.length; i++) 
    obj[arr[i]] == undefined ? obj[arr[i]] ++ : out.push(arr[i]);
  return out;
}  

Поскольку большую часть времени бесполезно возвращать ВСЕ дубликаты, а просто сообщать, какие существуют дублирующиеся значения. В этом случае вы возвращаете массив с уникальными дубликатами; -)

function GetDuplicates(arr) {
  var i, out=[], obj={};
  for (i=0; i < arr.length; i++)
    obj[arr[i]] == undefined ? obj[arr[i]] ++ : out.push(arr[i]);
  return GetUnique(out);
}

function GetUnique(arr) {
  return $.grep(arr, function(elem, index) {
    return index == $.inArray(elem, arr);
  });
}

Может быть, кто-то еще думает так же.

2 голосов
/ 02 апреля 2014

Модификация решения @ RaphaelMontanaro, заимствованная из блога @ Nosredna, вот что вы можете сделать, если вы просто хотите идентифицировать дубликаты элементов в вашем массиве.

function identifyDuplicatesFromArray(arr) {
        var i;
        var len = arr.length;
        var obj = {};
        var duplicates = [];

        for (i = 0; i < len; i++) {

            if (!obj[arr[i]]) {

                obj[arr[i]] = {};

            }

            else
            {
                duplicates.push(arr[i]);
            }

        }
        return duplicates;
    }

Спасибо за элегантное решение, @Nosredna!

2 голосов
/ 23 мая 2013

Я думаю, что ниже приведен самый простой и быстрый O (n) способ выполнить именно то, что вы просили:

function getDuplicates( arr ) {
  var i, value;
  var all = {};
  var duplicates = [];

  for( i=0; i<arr.length; i++ ) {
    value = arr[i];
    if( all[value] ) {
      duplicates.push( value );
      all[value] = false;
    } else if( typeof all[value] == "undefined" ) {
      all[value] = true;
    }
  }

  return duplicates;
}

Или для ES5 или выше:

function getDuplicates( arr ) {
  var all = {};
  return arr.reduce(function( duplicates, value ) {
    if( all[value] ) {
      duplicates.push(value);
      all[value] = false;
    } else if( typeof all[value] == "undefined" ) {
      all[value] = true;
    }
    return duplicates;
  }, []);
}
2 голосов
/ 02 августа 2014

Это, вероятно, один из самых быстрых способов окончательного удаления дубликатов из массива В 10 раз быстрее, чем большинство функций здесь. И в 78 раз быстрее в сафари

function toUnique(a,b,c){//array,placeholder,placeholder
 b=a.length;
 while(c=--b)while(c--)a[b]!==a[c]||a.splice(c,1)
}
var array=[1,2,3,4,5,6,7,8,9,0,1,2,1];
toUnique(array);
console.log(array);
  1. Тест: http://jsperf.com/wgu
  2. Демо: http://jsfiddle.net/46S7g/
  3. Подробнее: https://stackoverflow.com/a/25082874/2450730

если вы не можете прочитать приведенный выше код, спросите, прочитайте книгу по javascript или вот несколько объяснений более короткого кода. https://stackoverflow.com/a/21353032/2450730

EDIT Как указано в комментариях, эта функция возвращает массив с уникальными значениями, однако вопрос требует найти дубликаты. в этом случае простая модификация этой функции позволяет помещать дубликаты в массив, а затем с помощью предыдущей функции toUnique удаляет дубликаты дубликатов.

function theDuplicates(a,b,c,d){//array,placeholder,placeholder
 b=a.length,d=[];
 while(c=--b)while(c--)a[b]!==a[c]||d.push(a.splice(c,1))
}
var array=[1,2,3,4,5,6,7,8,9,0,1,2,1];

toUnique(theDuplicates(array));
2 голосов
/ 21 апреля 2017

Мне кажется, что самым простым решением было бы просто использовать indexOf

полный пример помещения в массив только уникальных элементов.

var arr = ['a','b','c','d','a','b','c','d'];
var newA = [];
for(var i = 0; i < arr.length; i++){
    if(newA.indexOf(arr[i]) === -1){
        newA.push(arr[i]);
    }
 }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...