Сравните неуказанное количество массивов для общих значений в JavaScript
Я хотел бы знать, как сравнить два или более - потенциально неограниченных - массива для общих значений и эффективно вставить эти значения в новый массив. Ниже у меня есть функция, которая будет принимать неограниченное количество аргументов, но я не уверен, что это хорошее место для начала. Похоже, в PHP есть метод, который может делать то, что я хочу, называемый array_intersect. Javascript предлагает что-то подобное?
Примечание: я нашел примеры того, как это можно сделать с двумя или около того массивами, но я не нашел примеров того, как такие подходы могут применяться к неопределенному количеству массивов на данный момент. Поэтому я не считаю это дублирующим вопросом.
Для дальнейшего уточнения массивы могут быть заполнены чем угодно. Буквы, цифры, символы, слова, вы называете это, это может быть там.
var sampleOne = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
var sampleTwo = [5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18];
function FindDirectRelation() {
for(var i = 0; i < arguments.length; ++i) {
console.log(arguments[i]);
};
};
var directRelation = FindDirectRelation(sampleOne, sampleTwo);
Я все еще начинающий программист, поэтому, пожалуйста, убедитесь, что все объясняется так, чтобы мне было достаточно просто это понять.
3 ответа
Используя существующее пересечение, которое работает с 2 массивами, мы можем связать вместе общее подмножество, используя встроенный reduce()
метод на массиве массивов, которые должны пересекаться:
function intersect(a, b) {
var aa = {};
a.forEach(function(v) { aa[v]=1; });
return b.filter(function(v) { return v in aa; });
}
var r1=[1,2,3],
r2=[1,3,4,5],
r3=[5,1,3];
alert([r1, r2, r3].reduce(intersect)) // shows: 1,3
если вы определяете "пересечение" как просто находящийся в нескольких массивах (не в каждом), то это более сложно...
Убедитесь, что элементы первого массива также находятся в остальных массивах:
function multi_intersect(a) {
var other_arrays = Array.prototype.slice.call(arguments, 1);
return a . filter(function(elt) {
return other_arrays.every(function(an) {
return an.indexOf(elt) !== -1;
});
});
}
Попробуйте использовать Array.prototype.filter()
, Array.prototype.indexOf()
var res = sampleOne.filter(function(val) {return sampleTwo.indexOf(val) !== -1})
var sampleOne = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
var sampleTwo = [5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18];
var arr = ["a", "b", "c"];
var arr1 = ["c", "d", "e"];
var arr2 = [2, 7];
function samples() {
var args = Array.prototype.slice.call(arguments);
var res = [];
for (var i = 0, curr, next; i < args.length; i++) {
if (args[i + 1]) {
// set `curr` to array `i`
curr = args[i];
// set `next` to array `i + 1` if it exists
next = args[i + 1]
} else {
// if at last index, set `curr` to `args` : input arrays
// flattened to single array , with element at `i` removed
curr = [].concat.apply([], args.slice(0, args.length - 1));
console.log(curr)
// set next to current index
next = args[i];
};
next = next.filter(function(val) {
return curr.indexOf(val) !== -1
// filter duplicate entries at `res`
&& res.indexOf(val) === -1
});
res = res.concat.apply(res, next);
};
return res
}
var sample = samples(sampleOne, sampleTwo, arr, arr1, arr2);
console.log(sample); // [5, 6, 7, 8, 9, 10, 11, 12, "c", 2]