Как объединить два массива в JavaScript и дедуплицировать элементы

Я знаю, что это довольно поздно, но нить помогла мне (в частности, предложение от @Dionysoos ), и надеюсь, что мой ответ может помочь другим.

У меня был тот же error ...

Start-Process : This command cannot be executed due to the error: The directory name is invalid.

... при запуске скрипта без присмотра, пока он работал в ISE.

Неавтоматический скрипт использовал пользовательский $env:TEMP в качестве рабочего каталога, что означало, что новый процесс не имел к нему доступа. Указание -WorkingDirectory $env:windir в команде Start-Process разрешило проблему.

1182
задан Peter Mortensen 18 October 2017 в 06:29
поделиться

9 ответов

Чтобы просто объединить массивы (без удаления дубликатов)

Версия ES5 используйте Array.concat :

 var array1 = ["Vijendra", "Singh" ]; var array2 = ["Сингх", "Шакья"]; console.log (array1.concat (array2)); 

Версия ES6 использует деструктурирование

const array1 = ["Vijendra","Singh"];
const array2 = ["Singh", "Shakya"];
const array3 = [...array1, ...array2];

Поскольку нет «встроенного» способа удаления дубликатов ( ECMA-262 фактически имеет Array.forEach , что было бы отлично для этого), мы должны сделать это вручную:

Array.prototype.unique = function() {
    var a = this.concat();
    for(var i=0; i<a.length; ++i) {
        for(var j=i+1; j<a.length; ++j) {
            if(a[i] === a[j])
                a.splice(j--, 1);
        }
    }

    return a;
};

Затем, чтобы использовать:

var array1 = ["Vijendra","Singh"];
var array2 = ["Singh", "Shakya"];
// Merges both arrays and gets unique items
var array3 = array1.concat(array2).unique(); 

Это также сохранит порядок массивов (т.е. сортировка не требуется).

Так как многих людей раздражает увеличение прототипа ] Array.prototype и for in , вот менее инвазивный способ его использования:

function arrayUnique(array) {
    var a = array.concat();
    for(var i=0; i<a.length; ++i) {
        for(var j=i+1; j<a.length; ++j) {
            if(a[i] === a[j])
                a.splice(j--, 1);
        }
    }

    return a;
}

var array1 = ["Vijendra","Singh"];
var array2 = ["Singh", "Shakya"];
    // Merges both arrays and gets unique items
var array3 = arrayUnique(array1.concat(array2));

Для тех, кому посчастливилось работать с браузерами, в которых доступен ES5, вы можете использовать Object.defineProperty следующим образом:

Object.defineProperty(Array.prototype, 'unique', {
    enumerable: false,
    configurable: false,
    writable: false,
    value: function() {
        var a = this.concat();
        for(var i=0; i<a.length; ++i) {
            for(var j=i+1; j<a.length; ++j) {
                if(a[i] === a[j])
                    a.splice(j--, 1);
            }
        }

        return a;
    }
});
1563
ответ дан 19 December 2019 в 20:14
поделиться

Существует столько решений для слияния двух массивов. Они могут быть разделены на две основных категории (кроме использования сторонних библиотек как lodash или underscore.js).

a) комбинируют два массива и удаляют дублированные объекты.

b) отфильтровывают объекты прежде, чем объединить их.

Объединение два массива и удаляют дублированные объекты

Объединение

// mutable operation(array1 is the combined array)
array1.push(...array2);
array1.unshift(...array2);

// immutable operation
const combined = array1.concat(array2);
const combined = [...array1, ...array2];    // ES6

Объединение

существует много путей к объединению массива, я лично предлагаю ниже двух методов.

// a little bit tricky
const merged = combined.filter((item, index) => combined.indexOf(item) === index);
const merged = [...new Set(combined)];

Отфильтровывают объекты прежде, чем объединить их

существует также много путей, но я лично предлагаю ниже кода из-за его простоты.

const merged = array1.concat(array2.filter(secItem => !array1.includes(secItem)));
3
ответ дан 19 December 2019 в 20:14
поделиться

Почему вы не используете объект? Похоже, вы пытаетесь смоделировать набор. Однако это не сохранит порядок.

var set1 = {"Vijendra":true, "Singh":true}
var set2 = {"Singh":true,  "Shakya":true}

// Merge second object into first
function merge(set1, set2){
  for (var key in set2){
    if (set2.hasOwnProperty(key))
      set1[key] = set2[key]
  }
  return set1
}

merge(set1, set2)

// Create set from array
function setify(array){
  var result = {}
  for (var item in array){
    if (array.hasOwnProperty(item))
      result[array[item]] = true
  }
  return result
}
14
ответ дан 19 December 2019 в 20:14
поделиться
//Array.indexOf was introduced in javascript 1.6 (ECMA-262) 
//We need to implement it explicitly for other browsers, 
if (!Array.prototype.indexOf)
{
  Array.prototype.indexOf = function(elt, from)
  {
    var len = this.length >>> 0;

    for (; from < len; from++)
    {
      if (from in this &&
          this[from] === elt)
        return from;
    }
    return -1;
  };
}
//now, on to the problem

var array1 = ["Vijendra","Singh"];
var array2 = ["Singh", "Shakya"];

var merged = array1.concat(array2);
var t;
for(i = 0; i < merged.length; i++)
  if((t = merged.indexOf(i + 1, merged[i])) != -1)
  {
    merged.splice(t, 1);
    i--;//in case of multiple occurrences
  }

Реализация метода indexOf для других браузеров взята из MDC

6
ответ дан 19 December 2019 в 20:14
поделиться

Новое решение (которое использует Array.prototype.indexOf и Array.prototype.concat ):

Array.prototype.uniqueMerge = function( a ) {
    for ( var nonDuplicates = [], i = 0, l = a.length; i<l; ++i ) {
        if ( this.indexOf( a[i] ) === -1 ) {
            nonDuplicates.push( a[i] );
        }
    }
    return this.concat( nonDuplicates )
};

Использование:

>>> ['Vijendra', 'Singh'].uniqueMerge(['Singh', 'Shakya'])
["Vijendra", "Singh", "Shakya"]

Массив. prototype.indexOf (для Internet Explorer):

Array.prototype.indexOf = Array.prototype.indexOf || function(elt)
  {
    var len = this.length >>> 0;

    var from = Number(arguments[1]) || 0;
    from = (from < 0) ? Math.ceil(from): Math.floor(from); 
    if (from < 0)from += len;

    for (; from < len; from++)
    {
      if (from in this && this[from] === elt)return from;
    }
    return -1;
  };
6
ответ дан 19 December 2019 в 20:14
поделиться

Можно создать Set spread луг эти два входных массива.

, Поскольку наборы не позволяют дублирующиеся элементы, это создаст объединение от от элементов в этих двух входных массивах.

, Например:

var arr1 = ['1', '2', '3']
var arr2 = ['3', '4', '5']

var arr3 = [...new Set([...arr1, ...arr2])]

console.log(arr3);
//(5) ["1", "2", "3", "4", "5"]
1
ответ дан 19 December 2019 в 20:14
поделиться

Я знаю, что этот вопрос не о массиве объектов, но искатели действительно заканчивают здесь.

, таким образом, стоит добавить для будущих читателей надлежащий способ ES6 объединиться и затем удалить дубликаты

массив объектов :

var arr1 = [ {a: 1}, {a: 2}, {a: 3} ];
var arr2 = [ {a: 1}, {a: 2}, {a: 4} ];

var arr3 = arr1.concat(arr2.filter( ({a}) => !arr1.find(f => f.a == a) ));

// [ {a: 1}, {a: 2}, {a: 3}, {a: 4} ]
1
ответ дан 19 December 2019 в 20:14
поделиться

ES2019

можно использовать его как union(array1, array2, array3, ...)

/**
 * Merges two or more arrays keeping unique items. This method does
 * not change the existing arrays, but instead returns a new array.
 */
function union<T>(...arrays: T[]) {
  return [...new Set([...arrays].flat())];
}

, Это - ES2019 из-за эти flat() функция, но можно использовать ядро-js для получения его как полизаливки. T вот является TypeScript универсальным типом, который можно удалить, если Вы не используете TypeScript. При использовании TypeScript удостоверьтесь, что добавили "lib": ["es2019.array"] к параметрам компилятора в tsconfig.json.

или...

просто lodash использования _ .union

0
ответ дан 19 December 2019 в 20:14
поделиться
   //1.merge two array into one array

   var arr1 = [0, 1, 2, 4];
   var arr2 = [4, 5, 6];

   //for merge array we use "Array.concat"

   let combineArray = arr1.concat(arr2); //output

   alert(combineArray); //now out put is 0,1,2,4,4,5,6 but 4 reapeat

   //2.same thing with "Spread Syntex"

   let spreadArray = [...arr1, ...arr2];

   alert(spreadArray);  //now out put is 0,1,2,4,4,5,6 but 4 reapete


   /*
       if we need remove duplicate element method use are
       1.Using set
       2.using .filter
       3.using .reduce
   */
0
ответ дан 19 December 2019 в 20:14
поделиться
Другие вопросы по тегам:

Похожие вопросы: