Advanced-Frontend / Daily-Interview-Question

我是依扬(木易杨),公众号「高级前端进阶」作者,每天搞定一道前端大厂面试题,祝大家天天进步,一年后会看到不一样的自己。
https://muyiy.cn/question/
27.41k stars 3.29k forks source link

第 142 题:(算法题)求多个数组之间的交集 #293

Open igoryaodev opened 5 years ago

igoryaodev commented 5 years ago

算法

igoryaodev commented 5 years ago

142

1042478910 commented 5 years ago

let a = new Set([1, 2, 3]); let b = new Set([4, 3, 2]); let intersect = new Set([...a].filter(x => b.has(x))); // set {2, 3}

Kisnnnnn commented 5 years ago
let setData1 = [1, 2, 3, 4],
  setData2 = [2, 3, 4, 9, 19, 91];

function mixedArr(...args) {
  let res = new Set(args[0]);
  if (args.length < 2) {
    return args[0];
  }
  for (let i = 1; i < args.length; i++) {
    const item = args[i];
    if (Object.prototype.toString.call(item).slice(8, -1) === 'Array') {
      let _arr = item.filter(e => res.has(e));
      if (_arr != [...res]) {
        res = new Set(_arr);
      }
    }
  }

  return [...res];
}

mixedArr(setData1, setData2, [2, 3]);
littleLane commented 5 years ago
function intersect(...args) {
  if (args.length === 0) {
    return []
  }

  if (args.length === 1) {
    return args[0]
  }

  return args.reduce((result, arg) => {
    return result.filter(item => arg.includes(item))
  })
}
zjtt commented 5 years ago
let getMix = arr => {
    return arr.reduce((total, item, index) => {
        if (index === 0) {
            return [...total, ...item]
        }
        else {
            return total.filter(v => item.includes(v))
        }
    }, [])
}
getMix([[1],[1,2],[1,3]]) //[1]
zxc6881553 commented 5 years ago

let array1 = [1,2,3,4,5,6]; let array2 = [2,3,4,5,6,8,9]; let array3 = [4,5,6,7,8,9] console.log(getIntersection(array1, array2, array3)); function getIntersection(){ let result = []; let obj = {}; let array = [].slice.apply(arguments) for(let i = 0; i < array.length; i++) { let arrayItem = array[i] for(let n = 0; n < arrayItem.length; n++) { if (obj[arrayItem[n]]) { obj[arrayItem[n]] = obj[arrayItem[n]] + 1 } else { obj[arrayItem[n]] = 1 } } }; for(let item in obj) { if(obj[item] > 1) { result.push(item) } }; return result; };

songkangle0826 commented 5 years ago

function intersection(...args){ if(args.length == 0) return []; if(args.length == 1) return args[0]; let arr = []; args.forEach((item)=>{ arr = arr.concat([...item]); }) // 并集 // return new Set(arr);

// 交集
let obj = {};
let result = [];
for(let i in arr){
    if(obj[arr[i]]){
        result.push(arr[i])
    }else{
        obj[arr[i]] = true;
    }
}
return result;

} intersection([1,2,3],[2,3]) // [2,3]

nowherebutup commented 5 years ago
const arr1 = [1, 2, 3];
const arr2 = [3, 4, 5];
const arr3 = [3, 6, 7];
const handle = (...arr) => {
  return arr.reduce((rst, ele, i) => {
    return rst.filter(item => ele.includes(item));
  });
}

handle(arr1, arr2, arr3);
DarthVaderrr commented 5 years ago

输入的数组有可能出现重复数据,需要多一步判断;如果输入的是集合,就不用这么复杂了


function intersectN(...arrs) {
    if (arrs.length === 1) return arrs[0];
    if (arrs.length === 2) return intersect2(...arrs);//如果只有两个 无需reduce 直接求
    return arrs.reduce((a, b) => b = intersect2(a, b))
}

function intersect2(nums1, nums2) {
    //求两个数组的交叉数组
    let res = [];
    let obj = toMap(nums1);
    for (let i of nums2) {
        if (obj[i]) {
            res.push(i)
            obj[i]--
        }
    }
    return res;
}

function toMap(arr) {
    //辅助函数  用于将数组转成map 键值分别是元素和其数量
    let obj = {}
    for (let i of arr) {
        if (obj[i]) obj[i]++
        else obj[i] = 1
    }
    return obj
}

let arr1 = [1, 2, 3, 4, 5, 6, 7, 1, 5]
let arr2 = [3, 5, 4, 1, 5]
let arr3 = [5, 7, 1, 3, 1, 5]

console.log(intersectN(arr1, arr2, arr3)) //[ 5, 1, 3, 5 ] 
EnergySUD commented 5 years ago
function intersection(){
    let min_arr=arguments[0],intersect=[];
    for (let i=0;i<arguments.length;i++) {
        if(min_arr.length > arguments[i].length){ min_arr = arguments[i];}
    }
    for(let i=0;i<min_arr.length;i++){
        let flag = true;
        for (let j=0;j<arguments.length;j++) {
            if(!arguments[j].includes(min_arr[i])){
                flag = false;break;
            }
        }
        if(flag){ 
            if(!intersect.includes(min_arr[i])){ 
                intersect.push(min_arr[i]) 
            }
        }
    }
    return intersect
}
let arr = [1,2,3,4,5,6,7,8,9,10,10],arr1=[5,4,2,9,3,7,21],arr2=[9,3,5,4,11,3];
console.log(intersection(arr,arr1,arr2)) // [9, 3, 5, 4]
guestccc commented 5 years ago

处理数组

var a = [1, 2, 3, 5]
var b = [2, 4, 5, 1]
var c = [1, 3, 5]
var intersect
function fn(...arg){
  intersect =  arg.reduce((total,next)=>{return total.filter(item=>next.includes(item))})
}
fn(a,b,c)
console.log(intersect)
// [1,5]

处理数组和类数组(有iterable接口的数据结构)

var intersect
function fn2 (...arg){
    intersect = arg.reduce((total,next)=>{return [...total].filter(item=>new Set(next).has(item))})
}
var a = [1, 2, 3, 5]
var b = [2, 4, 5, 1]
var c = [1, 3, 5]
fn2(a,b,c)
console.log(intersect)
// [1,5]

a = new Set([1, 2, 3, 5])
b = new Set([2, 4, 5, 1])
c = new Set([1, 3, 5])
fn2(a,b,c)
console.log(intersect)
//[1,5]
Minsaint commented 5 years ago
function getSameItem(arr, ...rest) {
    return arr.filter(item => rest.every(restArr => restArr.indexOf(item) > -1))
}
igoryaodev commented 5 years ago

const p1 = [ { id: 123 }, { id: 124 }, { id: 125 }, ] const p2 = [ { id: 124 }, { id: 125 }, { id: 125 }, { id: 126 }, ] const p3 = [ { id: 125 }, { id: 128 }, { id: 128 }, ] let a = intersections([p1, p2, p3]) console.log(a)

function intersections(options) {
  if (!Array.isArray(options) || !options.length) return;
  let arrLength = options.length;
  let result = [];
  let cacheFirstResult = [];
  let arr = [];
  let l = 0;
  let obj = {};
  let obj1 = {}

  function initState(arr) {
    let l = arr.length;
    while(l) {
      l--;
      obj1[arr[l].id] = true;
    }
  }
  initState(options[0])

  while (arrLength--) {
    arr = options[arrLength];
    l = arr.length;
    while (l) {
      l--;
      if (obj1[arr[l].id]) {
        obj[arr[l].id] = true;
        if (arrLength === options.length - 1)
          cacheFirstResult.push(arr[l])
      }
    }
    obj1 = {...obj}
    obj = {}

  }
  return cacheFirstResult.filter(v => {
    if (Object.keys(obj1).indexOf(v.id.toString()) !== -1) return v;
  })
}
snoweini commented 5 years ago

var arr=[1,2,3] var arr2=[2,3,4,5] var arr3 = [3,4,5,6] var arr4 = [6,4,1,2] function selectArr(arr1,arr2){ var narr = []; for(var i = 0; i<arr1.length; i++){ for(var j = 0; j<arr2.length; j++){ if(arr1[i]===arr2[j]&&narr.indexOf(arr2[j])==-1){ narr.push(arr2[j]) } } } return narr }

function setArr(...arg){ if(arg.length===0){ return false } if(arg.length===1){ return arg[0] } if(arg.length>1){ for(var i = 1; i<arg.length; i++){ arg[i] = selectArr(arg[i-1],arg[i]) }

} return arg[arg.length-1]; } console.log(setArr(arr2,arr3))

qq1037305420 commented 5 years ago

如果是对象数组上面是不是好多都不管用了

muzishuiji commented 5 years ago
function getSamePart() {
    let samePart = [], countMap = new Map();
    let args = [...arguments], len = args.length;
    args.reduce((arr, cur) => {
        return Array.isArray(cur) ? arr.concat(cur) : arr;
    }, []).forEach(item => {
        countMap.has(item) ? 
                 countMap.set(item, countMap.get(item) + 1) : countMap.set(item, 1)
    })
    for(let item of countMap) {
        if(item[1] >= len) {
            samePart.push(item[0])
        }
    }
    return samePart;
}
getSamePart(['1', '2', 1,2,3], ['1','2',1,2], ['1','2',3,4,5]);    // ['1', '2']
azl397985856 commented 5 years ago

Clarify

Since the description kind of loose, So Let's make it clear.

Suppose that, all the list are unique , eg: [1,2,2,3] is not allow.Otherwise the solution could be quiet ugly.

Concise Solution - reduce

initially, we can set the answer to be the very first item of the list.

eg: [1,2,3], [1,2,3,5], [1] , we take [1,2,3] as the initial value(the answer can't be greater than it). then we keep filtering repeatedly

If U'r not familar with reduce, PLZ check the MDN Doc

const intersection = (...list) => list.reduce((acc, cur) => acc.filter(ele => cur.includes(ele)))

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

More efficient and Easy to understand

function intersection(...list) {
  const mapper = new Map();
  const res = [];
  for (ele of list) {
    for (n of ele) {
      if (mapper.get(n) === void 0) {
        mapper.set(n, 1);
      } else {
        mapper.set(n, mapper.get(n) + 1);
      }
    }
  }

  for ([k, cnt] of mapper.entries()) {
    if (cnt === list.length) res.push(k);
  }

  return res;
}

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

Thanks for your reading, if like it, Give Me a thumb up 👍 and follow me on GitHub repo - frontend-interview

anjingdeyikexin commented 5 years ago

let a = [1, 2, 3]; let b = [4, 3, 2]; let result=a.filter((e)=>{ return b.includes(e) }) console.log(result) //[2,3]

Fzzzzy commented 5 years ago
function findJoin(...rest) {
    if (rest.length === 0) return [];

    return Array.from(rest.reduce((result, arr) => {
        return new Set(result.filter(item => arr.includes(item)))
    }))
}
NANAYWY commented 5 years ago

function intersect(...arg) {
return arg.reduce((com, next) => com.filter(item => next.includes(item)));
}
fengshenhai-0727 commented 5 years ago

function inersection(a,b){
    if(!a.length || !b.length){
        return [];
    }
    const map = {};
    const result = [];
    for(let i=0; i<a.length; i++){
        map[a[i]] = map[a[i]] ? ++map[a[i]] : 1;
    }
    for(let i=0; i<b.length; i++){
        if(map[b[i]]){
            result.push(b[i]);
            map[b[i]]--;
        }
    }
    return result
}

function inersections(){
    if(arguments.length<2){
        return [];
    }
    const args = Array.prototype.slice.call(arguments);
    const result = [];
    let temp = inersection(args[0],args[1]);
    let i = 2;
    while(i<args.length){
        temp=inersection(temp,args[i])
        i++;
    }
    return temp;
}
inersections([1,2,2,1],[2,2],[2,2,4],[2]);//2
spongege commented 4 years ago
  const a = [1, 2, 2, 3]
  const b = [2, 2, 3, 4, 5]
  const c = [2, 2, 3, 6, 7, 2]

  const intersect = (...args) =>
    args.reduce(
      (acc, cur) => acc.filter(val => cur.includes(val)),
      args[0] || []
    )
  console.log(intersect(a, b, c))
lx812833 commented 4 years ago
const arr1 = [1, 2, 3];
const arr2 = [3, 4, 5];
const arr3 = [3, 6, 7];
const handle = (...arr) => {
  return arr.reduce((rst, ele, i) => {
    return rst.filter(item => ele.includes(item));
  });
}

handle(arr1, arr2, arr3);

在返回结果那里应该做一个去重

xiaowuge007 commented 4 years ago
let arr1 = [1,2,3,4,5];
        let arr2 = [2,4,6,8,7];
        let arr3 = [3,2,5,6,9,10,2];
        let arr4 = [10,23,4,56,1,2];
        let arr5 = [1,4,8,70,2];
        function fn(...arg) {
            let a = new Set(arg[0]);
            for(let i = 1;i<arg.length;i++){
                let arr = Array.from(a)
                for(let k = 0;k<arr.length;k++){
                    if(arg[i].indexOf(arr[k]) === -1){
                        a.delete(arr[k])
                    }
                }
            }
            return Array.from(a);
        }
        console.log(fn(arr1,arr2,arr3,arr4,arr5))
coveyz commented 4 years ago

给定两个数组,编写一个函数来计算它们的交集。

const intersect3 = (nums1,nums2) => { 
  let result = []
  for (const num of nums1) {
    let idx = nums2.indexOf(num)
    if (idx > -1) {
      result.push(num)
      nums2.splice(idx,1)
    }
  }
  return result
}

console.log(intersect3([4,9,5],[9,4,9,8,4]));

purplepeng commented 4 years ago
function intersect(...arrays) {
  let set = new Set(arrays[0])   
  for(let i=1; i< arrays.length; i++) {
    let tmpSet = new Set(arrays[i])
    set = new Set([...set].filter(x => tmpSet.has(x)))    
  }
  return [...set]
}

var items = intersect([1, 2, 3, 4], [2, 3, 4, 5], [3, 4, 5, 6])
console.log(items)
bbrucechen commented 4 years ago
function intersection(args1,...args) {
  args1 = [...new Set(args1)]
  const result = []
  for(let i = 0;i < args1.length;i ++) {
    let flag = true
    args.forEach(value => {
      if(!value.includes(args1[i])) {
        flag = false
      }
    })
    if(flag) {
      result.push(args1[i])
    }
  }
  return result
}

console.log(intersection([1,1,1,2,2,3,4,5,5],[1,2,3],[2,3,4],[6,9,2])) // [2]
goodmanforweb commented 4 years ago

Clarify

Since the description kind of loose, So Let's make it clear.

Suppose that, all the list are unique , eg: [1,2,2,3] is not allow.Otherwise the solution could be quiet ugly.

Concise Solution - reduce

initially, we can set the answer to be the very first item of the list.

eg: [1,2,3], [1,2,3,5], [1] , we take [1,2,3] as the initial value(the answer can't be greater than it). then we keep filtering repeatedly

If U'r not familar with reduce, PLZ check the MDN Doc

const intersection = (...list) => list.reduce((acc, cur) => acc.filter(ele => cur.includes(ele)))

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

More efficient and Easy to understand

  • track the repeating count, store into Map as [k=item, v=count]
  • finally, remove all the items which repeating counts not equals to the size of the list(WHY?)
function intersection(...list) {
  const mapper = new Map();
  const res = [];
  for (ele of list) {
    for (n of ele) {
      if (mapper.get(n) === void 0) {
        mapper.set(n, 1);
      } else {
        mapper.set(n, mapper.get(n) + 1);
      }
    }
  }

  for ([k, cnt] of mapper.entries()) {
    if (cnt === list.length) res.push(k);
  }

  return res;
}

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

Thanks for your reading, if like it, Give Me a thumb up 👍 and follow me on GitHub repo - frontend-interview

your code has bug,see example intersection([1,2,1],[3,4]) // [1]

azl397985856 commented 4 years ago

Clarify

Since the description kind of loose, So Let's make it clear. Suppose that, all the list are unique , eg: [1,2,2,3] is not allow.Otherwise the solution could be quiet ugly.

Concise Solution - reduce

initially, we can set the answer to be the very first item of the list. eg: [1,2,3], [1,2,3,5], [1] , we take [1,2,3] as the initial value(the answer can't be greater than it). then we keep filtering repeatedly

If U'r not familar with reduce, PLZ check the MDN Doc

const intersection = (...list) => list.reduce((acc, cur) => acc.filter(ele => cur.includes(ele)))

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

More efficient and Easy to understand

  • track the repeating count, store into Map as [k=item, v=count]
  • finally, remove all the items which repeating counts not equals to the size of the list(WHY?)
function intersection(...list) {
  const mapper = new Map();
  const res = [];
  for (ele of list) {
    for (n of ele) {
      if (mapper.get(n) === void 0) {
        mapper.set(n, 1);
      } else {
        mapper.set(n, mapper.get(n) + 1);
      }
    }
  }

  for ([k, cnt] of mapper.entries()) {
    if (cnt === list.length) res.push(k);
  }

  return res;
}

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

Thanks for your reading, if like it, Give Me a thumb up +1 and follow me on GitHub repo - frontend-interview

your code has bug,see example intersection([1,2,1],[3,4]) // [1]

认真看我的前提,谢谢

wuaixiaoyao commented 4 years ago
function getIntersection (...args) {
  //判读是一个还是多个数组
  if (args.length > 1) {
    return args.reduce((pre, cur)=> {
       let preResult = [...new Set(pre)].filter(item => cur.includes(item) );
       //用数组的 includes 或者 set 的has方法验证
       //let preResult = [...new Set(pre)].filter(item => new Set(cur).has(item) );
       return preResult 
    })
  } else {  
    return args[0]
  }

}
console.log(getIntersection([1,2,2,3], [2,2,3,4,5],[3,4,5])
)
jojomango commented 4 years ago
const a = [1,2,3,1,4,5], b = [3,3,2,5], c = [1,1,1,3,2];
const uniq = arr => [...new Set(arr)];
const mix = (arg1,...arrs) => {
  const uniqArr = uniq(arg1);
  return arrs.reduce((result, arr) => {
    return result.filter(ele => arr.includes(ele));
  }, uniqArr);
};

console.log(mix(a,b,c)); // [2,3]
fzhange commented 4 years ago
function fun(...arg){
  let myArr = arg.map(item=>[...new Set(item)]
  )
  let myData = myArr.reduce((pre,curr)=>{
    return pre.map((item)=>{
      if(curr.indexOf(item) != -1) return item;
    }).filter((item)=>!!item)
  })
  return myData;
}

console.log('fun([1,2,2,3,4,4],[2,1,2,4],[2,1])  : ', fun([1,2,2,3,4,4],[2,1,2,4],[2,1])  ); //[1,2]
meta07 commented 4 years ago

参考@fengshenhai-0727大兄弟的,即使数组有重复的交集项也没问题。

function getTwoArrsCommon(arr1, arr2) {
    if(!arr1.length || !arr2.length) {
        return [];
    }
    const res = [];
    const map = {};
    for(let k of arr1) {
        if(map[k]) {
            map[k]++;
        } else {
            map[k] = 1;
        }
    }
    for(let k of arr2) {
        if(map[k] > 0) {
            res.push(k);
            map[k]--;
         }
    }
    return res;
}
function getManyArrsCommon() {
    if(arguments.length < 2) {
        return [];
    }
    const args = Array.from(arguments);
    let res = getTwoArrsCommon(args[0], args[1]);
    let i = 2;
    while(i < args.length) {
        res = getTwoArrsCommon(res, args[i]);
        i++;
    }
   return res;
}
getManyArrsCommon([1,2,2,1],[2,2],[2,2,4],[2]); // [2]
getManyArrsCommon([1,1,2,3], [1,1,1,2,3,5,5], [1,1]); // [1, 1]
getManyArrsCommon([1,1,3,5,5], [2, 4, 5], [3, 5, 5]); // [5]
cutie6 commented 4 years ago

处理数组

var a = [1, 2, 3, 5]
var b = [2, 4, 5, 1]
var c = [1, 3, 5]
var intersect
function fn(...arg){
  intersect =  arg.reduce((total,next)=>{return total.filter(item=>next.includes(item))})
}
fn(a,b,c)
console.log(intersect)
// [1,5]

处理数组和类数组(有iterable接口的数据结构)

var intersect
function fn2 (...arg){
    intersect = arg.reduce((total,next)=>{return [...total].filter(item=>new Set(next).has(item))})
}
var a = [1, 2, 3, 5]
var b = [2, 4, 5, 1]
var c = [1, 3, 5]
fn2(a,b,c)
console.log(intersect)
// [1,5]

a = new Set([1, 2, 3, 5])
b = new Set([2, 4, 5, 1])
c = new Set([1, 3, 5])
fn2(a,b,c)
console.log(intersect)
//[1,5]

如果第一个数组中有重复的两个1呢,这样算出来,交集中也会有两个1吧

cutie6 commented 4 years ago

Clarify

Since the description kind of loose, So Let's make it clear.

Suppose that, all the list are unique , eg: [1,2,2,3] is not allow.Otherwise the solution could be quiet ugly.

Concise Solution - reduce

initially, we can set the answer to be the very first item of the list.

eg: [1,2,3], [1,2,3,5], [1] , we take [1,2,3] as the initial value(the answer can't be greater than it). then we keep filtering repeatedly

If U'r not familar with reduce, PLZ check the MDN Doc

const intersection = (...list) => list.reduce((acc, cur) => acc.filter(ele => cur.includes(ele)))

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

More efficient and Easy to understand

  • track the repeating count, store into Map as [k=item, v=count]
  • finally, remove all the items which repeating counts not equals to the size of the list(WHY?)
function intersection(...list) {
  const mapper = new Map();
  const res = [];
  for (ele of list) {
    for (n of ele) {
      if (mapper.get(n) === void 0) {
        mapper.set(n, 1);
      } else {
        mapper.set(n, mapper.get(n) + 1);
      }
    }
  }

  for ([k, cnt] of mapper.entries()) {
    if (cnt === list.length) res.push(k);
  }

  return res;
}

// test
intersection([1,2,3], [1,2,3,5], [1]) // [1]

Thanks for your reading, if like it, Give Me a thumb up 👍 and follow me on GitHub repo - frontend-interview

中国人为啥要用英文

cutie6 commented 4 years ago

function intersection(...args){ if(args.length == 0) return []; if(args.length == 1) return args[0]; let arr = []; args.forEach((item)=>{ arr = arr.concat([...item]); }) // 并集 // return new Set(arr);

// 交集
let obj = {};
let result = [];
for(let i in arr){
  if(obj[arr[i]]){
      result.push(arr[i])
  }else{
      obj[arr[i]] = true;
  }
}
return result;

} intersection([1,2,3],[2,3]) // [2,3]

这种算法,[1,1,1,] 和 [] 算出来岂不是 [1,1,1]

cutie6 commented 4 years ago
function intersection(){
  let min_arr=arguments[0],intersect=[];
  for (let i=0;i<arguments.length;i++) {
      if(min_arr.length > arguments[i].length){ min_arr = arguments[i];}
  }
  for(let i=0;i<min_arr.length;i++){
      let flag = true;
      for (let j=0;j<arguments.length;j++) {
          if(!arguments[j].includes(min_arr[i])){
              flag = false;break;
          }
      }
      if(flag){ 
          if(!intersect.includes(min_arr[i])){ 
              intersect.push(min_arr[i]) 
          }
      }
  }
  return intersect
}
let arr = [1,2,3,4,5,6,7,8,9,10,10],arr1=[5,4,2,9,3,7,21],arr2=[9,3,5,4,11,3];
console.log(intersection(arr,arr1,arr2)) // [9, 3, 5, 4]

这样算的话,那[1,1,1,2] 和 [1,1,1,] 的交集只有1了

NathanHan1 commented 4 years ago
function intersection(...arr) {
        // 注意 交集是集合概念,集合是不存在重复元素的
        const map = {}
        const len = arr.length
        const result = []
        for(let i = 0; i < len; i++) {
          const subArr = arr[i]
          for (let j = 0 ; j< subArr.length; j++) {
            const v = subArr[j]
            if(!map[v]) {
              map[v] = 1
            } else {
              map[v] += 1
            }
          }
        }
        for(let key in map) {
          if(map[key] === len) {
            result.push(~~key)
          }
        }
        return result
      }
dice246 commented 4 years ago
// 求多个数组之间的交集
function intersection(arr1, arr2) {
  let s1 = new Set([...arr1]);
  let s2 = new Set([...arr2]);
  let result = []

  for (let item of s1.values()) {
    if (s2.has(item)) {
      result.push(item)
    }
  }

  return result;
}

const arr1 = [1,2,3,4,5];
const arr2 = [3,6,7];
const result = intersection(arr1, arr2);
console.log(result);
ustchcl commented 4 years ago
// 不使用set

function intersect<A>(arr1: Array<A>, arr2: Array<A>): Array<A> {
  return arr2.filter(x => arr1.indexOf(x) !== -1)
}

// 递归
function intersectAll<A>(arr: Array<Array<A>>): Array<A> {
  if (arr.length === 0) return []
  else if (arr.length === 1) return arr[0]
  else {
    const sp = Math.floor(arr.length / 2)
    return intersect(intersectAll(arr.slice(0, sp)), intersectAll(arr.slice(sp)))
  }
}

// 迭代
function intersectAllReduce<A>(arr: Array<Array<A>>): Array<A> {
  if (arr.length === 0) return []
  else return arr.slice(1).reduce((pv, cv) => intersect(pv, cv), arr[0])
}
gitwillsky commented 4 years ago
function intersect(...arrays) {
  if (!arrays) {
    return [];
  }
  if (arrays.length === 1) {
    return arrays[0];
  }

  const m = new Map();

  for (let i = 0; i < arrays.length; i++) {
    for (let j = 0; j < arrays[i].length; j++) {
      const key = arrays[i][j];
      const value = i + 1;
      if (i === 0) {
        m.set(key, value);
        continue;
      }
      if (m.has(key) && m.get(key) < value) {
        m.set(key, value);
      }
    }
  }
  return Array.from(m.keys()).filter((key) => m.get(key) === arrays.length);
}
shizhenbin commented 4 years ago
function intersect(...args) {
  if (args.length === 0) {
    return []
  }

  if (args.length === 1) {
    return args[0]
  }

  return args.reduce((result, arg) => {
    return result.filter(item => arg.includes(item))
  })
}

console.log(intersect([1,1,1,1,1,2,9,63],[43,1,3,8],[3,3,3,,1,2,4,1,2])) //[1, 1, 1, 1, 1] 这个得到的不算是交集吧

yangchaojie456 commented 4 years ago

你们都好聪明,我只会笨方法

console.log(intersection([1, 1, 1, 1, 1, 2, 9, 63], [43, 1, 3, 8], [3, 3, 3, , 1, 2, 4, 1, 2]))

function intersection() {
    var map = new Map()
    for (var i = 0; i < arguments.length; i++) {
        var arr = [...new Set(arguments[i])]
        for (var j = 0; j < arr.length; j++) {
            if (!map.has(arr[j])) {
                map.set(arr[j], 1)
            } else {
                map.set(arr[j], map.get(arr[j]) + 1)
            }
        }
    }
    var collect = []
    for (const iterator of map) {
        if (iterator[1] == arguments.length) {
            collect.push(iterator[0])
        }
    }
    return collect
}
Godguns commented 3 years ago

`function choose(...arr) { let temp = [...arr].flat().sort((a, b) => { return a - b; });

let ret = []; for (let i = 0; i < temp.length; i++) { if (temp[i] == temp[i + 1]) { ret.push(temp[i]); } } console.log(ret); } let a = [1, 3, 4, 5]; let b = [1, 2, 3, 4, 5]; choose(a, b); `

pan-Z2l0aHVi commented 3 years ago
/**
 * 数组交集
 * @param  {...Array} arrays
 */
function arrayIntersection(...arrays) {
  if (arrays.length === 0) return []
  if (arrays.length === 1) return arrays[0]

  return arrays.reduce(
    (acc, cur) => (acc = acc.filter((accItem) => cur.some((curItem) => curItem === accItem)))
    // 或者 (acc, cur) => (acc = acc.filter((accItem) => cur.includes(accItem)))
  )
}

/**
 * test
 */
const res = arrayIntersection([1, 2, 3, 4, 5], [3, 4, 5, 6, 7], [4, 5, 6, 7, 8])
console.log('res: ', res) // [4, 5]
wenchao0809 commented 3 years ago

用分治代码比较简洁, 没考虑性能啥的

function intersection(...args) {
  if (args.length === 1) return args[0]
  if (args.length == 2) return [...new Set(args[0].filter(item => args[1].indexOf(item) !== -1))]
  const mid = Math.floor(args.length / 2)
  const left = intersection.apply(null, args.slice(0, mid))
  const right = intersection.apply(null, args.slice(mid))
  return intersection.apply(null, [left, right])
}
qzruncode commented 3 years ago
思想来源:借鉴vue diff源码
function intersectionArr(...params) {
    let itemCountMap = [];
    params.forEach(arr => {
      arr.forEach(item => {
        itemCountMap[item] = (itemCountMap[item] ? itemCountMap[item] : 0) + 1;
      })
    })

    let itArr = [];
    itemCountMap.forEach((item, index) => {
      if(item == params.length) {
        itArr.push(index);
      }
    })
    return itArr;
  }
  intersectionArr([1,2,3,4], [2,3], [2,3,4], [1,2,3] );
poppydani commented 3 years ago
function intersect(...args) {
  const flattened = args.reduce((res, arr) => {
    return res.concat(arr);
  }, []);
  return [...new Set(flattened)].filter((v) =>
    args.every((arr) => arr.includes(v))
  );
}
miniflycn commented 2 years ago
function mix(...arrs) {
    function createMap(arr) {
        return arr.reduce((result, value) => {
            result[value] = result[value] || 0
            result[value]++
            return result
        }, {})
    }

    const mapList = arrs.map(createMap)
    const res = mapList.shift()

    mapList.reduce((result, map) => {
        for (let key in result) {
            if (map[key]) {
                result[key] = Math.min(map[key], result[key])
            } else {
                delete result[key]
            }
        }
        return result
    }, res)

    const result = []

    for (let key in res) {
        while (res[key]--) {
            result.push(key)
        }
    }

    return result
}
Dylan0916 commented 2 years ago
function foo(...args) {
  return args.slice(1).reduce(
    (acc, cur) => {
      return acc.filter((v) => new Set(cur).has(v));
    },
    [...new Set(args[0])]
  );
}

foo([1, 2, 3], [3, 1, 4, 5, 6, 7], [1, 4, 5, 3]); // [1,3]