数组去重

118 阅读2分钟

数组去重的常用方法

1.indexOf

  • 利用数组的key属性,遍历对象,查找数组中是否存在这个属性,不存在则返回新数组中

  • 优点是效率高,缺点是使用了额外空间

          // 普通数组
          const arr = [11'1'17truetruefalsefalse'true''a', {}, {}];
          let newArr = [];
          arr.forEach(item=>{
            if(newArr.indexOf(item)<0){
             newArr.push(item)
            }
          }) 
          console.log(newArr);// [1, '1', 17, true, false, 'true', 'a', {}, {}]   
          
         // 对象数组 
          let arrObj = [
              { name: "小红", id: 1 },
              { name: "小橙", id: 1 },
              { name: "小黄", id: 4 },
              { name: "小绿", id: 3 },
              { name: "小青", id: 1 },
              { name: "小蓝", id: 4 }
          ];
          function fn2(tempArr) {
              let newArr = [];
              for (let i = 0; i < tempArr.length; i++) {
                  if (newArr.indexOf(tempArr[i].id) == -1) {
                      newArr.push(tempArr[i].id);
                  } else {
                      tempArr.splice(i, 1);
                      i--;
                  };
              };
              return tempArr;
          };
          console.log(fn2(arrObj));
          // [ { name: '小红', id: 1 }, { name: '小黄', id: 4 }, { name: '小绿', id: 3 } ]
    

2.new Set()

  • Set是一系列无序、没有重复值的数据集合,传入一个需要去重的数组,Set会自动删除重复的元素,再将Set转数组返回
  • 效率高,代码清晰,缺点是存在兼容性问题
// 普通数组
const arr = [11'1'17truetruefalsefalse'true''a', {}, {}];
const newArr = [...new Set(arr)];
console.log(newArr);// [1, '1', 17, true, false, 'true', 'a', {}, {}]  

3.new Map()

  • 利用Map的键值对同名覆盖,再将Map转数组
// 普通数组
const arr = [11'1'17truetruefalsefalse'true''a', {}, {}];
const m = new Map();
for (let i = 0; i < arr.length; i++) {
    m.set(arr[i], arr[i]);
}
const newArr = []
m.forEach(function (value, key) {
    newArr .push(value)
})
console.log(newArr );//[1, '1', 17, true, false, 'true', 'a', {}, {}]
// 对象数组

let arrObj = [
    { name: "小红", id: 1 },
    { name: "小橙", id: 1 },
    { name: "小黄", id: 4 },
    { name: "小绿", id: 3 },
    { name: "小青", id: 1 },
    { name: "小蓝", id: 4 }
];
// 方法一:
let map = new Map();
for (let item of arrObj) {
    if (!map.has(item.id)) {
        map.set(item.id, item);
    };
};
arr = [...map.values()];
console.log(arr);
// [ { name: '小红', id: 1 }, { name: '小黄', id: 4 }, { name: '小绿', id: 3 } ]
 
// 方法二: (代码较为简洁)
const map = new Map();
const newArr = arrObj.filter(v => !map.has(v.id) && map.set(v.id, 1));
console.log(newArr);
// [ { name: '小红', id: 1 }, { name: '小黄', id: 4 }, { name: '小绿', id: 3 } ]

4.filter() + indexof

  • filter把接收的函数依次作用于每一个数组项,然后根据返回值 true or false 决定是否保留该值
  • 优点在于可在去重时插入对元素的操作,可拓展性强
// 普通数组
const arr = [11'1'17truetruefalsefalse'true''a', {}, {}];
const newArr= arr.filter(function(item,index,self){
    return self.indexOf(item) === index;
})
console.log(newArr);//  [1, '1', 17, true, false, 'true', 'a', {}, {}]

5.reduce() + includes

  • reduce()把结果继续和序列的下一个元素做累加计算
  • 利用reduce遍历和传入一个空数组作为去重后的新数组,然后内部判断新数组中是否存在当前遍历的元素,不存在就插入新数组
  • 缺点在于时间消耗多,内存空间也额外占用
// 普通数组
const arr = [11'1'17truetruefalsefalse'true''a', {}, {}];
const newArray = arr.reduce((newArr, element) => {
  if (!newArr.includes(element)) {
    newArr.push(element);
  }
   return newArr;
}, []);

6.双层for循环

// 普通数组


// 对象数组
let arrObj = [
    { name: "小红", id: 1 },
    { name: "小橙", id: 1 },
    { name: "小黄", id: 4 },
    { name: "小绿", id: 3 },
    { name: "小青", id: 1 },
    { name: "小蓝", id: 4 }
];
function fn1(tempArr) {
    for (let i = 0; i < tempArr.length; i++) {
        for (let j = i + 1; j < tempArr.length; j++) {
            if (tempArr[i].id == tempArr[j].id) {
                tempArr.splice(j, 1);
                j--;
            };
        };
    };
    return tempArr;
};
console.log(fn1(arrObj)); 
// [ { name: '小红', id: 1 }, { name: '小黄', id: 4 }, { name: '小绿', id: 3 } ]

7.reduce 对象数组去重

let arr = [
            {
                key:'1',
                name:'林青霞'
            },
            {
                key:'2',
                name:'张三丰'
            },
            {
                key:'1',
                name:'段誉'
            },
            {
                key:'3',
                name:'林青霞'
            },
        ]
        // 封装方法:根据提供的属性去重
        function arrDistinctByProp(arr,prop){
            let obj = {};
            return arr.reduce(function(preValue,item){
                obj[item[prop]] ? '' : obj[item[prop]] = true && preValue.push(item);
                return preValue
            },[])
        }
        // 根据name去重
        let newArr = arrDistinctByProp(arr,'name')
        // 打印返回的新数组
        console.log(newArr) 
            [{
                key:'1',
                name:'林青霞'
            },
            {
                key:'2',
                name:'张三丰'
            },
            {
                key:'1',
                name:'段誉'
            }]

8.filter 对象数组去重

 let arr = [
            {
                key:'1',
                name:'林青霞'
            },
            {
                key:'2',
                name:'张三丰'
            },
            {
                key:'1',
                name:'段誉'
            },
        ]
        let res = arr.filter(function(item,index,self){
            return self.findIndex(el=>el.key==item.key)===index
        })
        console.log(res) // [ { key: '1', name: '林青霞' }, { key: '2', name: '张三丰' } ]  

  let arr = [
            {
                key:'1',
                name:'林青霞'
            },
            {
                key:'2',
                name:'张三丰'
            },
            {
                key:'1',
                name:'段誉'
            },
            {
                key:'1',
                name:'段誉'
            }
        ]
        function arrDistinctByProp(arr,prop){
            return arr.filter(function(item,index,self){
                return self.findIndex(el=>el[prop]==item[prop])===index
            })
        }
        //通过name属性去重
        let res = arrDistinctByProp(arr,'name')
        console.log(res);
        [
          { key: '1', name: '林青霞' },
          { key: '2', name: '张三丰' },
          { key: '1', name: '段誉' }
        ]  

9. 对象访问属性的方法

let arrObj = [
    { name: "小红", id: 1 },
    { name: "小橙", id: 1 },
    { name: "小黄", id: 4 },
    { name: "小绿", id: 3 },
    { name: "小青", id: 1 },
    { name: "小蓝", id: 4 }
];
function fn3(tempArr) {
    let result = [];
    let obj = {};
    for (let i = 0; i < tempArr.length; i++) {
        if (!obj[tempArr[i].id]) {
            result.push(tempArr[i]);
            obj[tempArr[i].id] = true;
        };
    };
    return result;
};
console.log(fn3(arrObj));
// [ { name: '小红', id: 1 }, { name: '小黄', id: 4 }, { name: '小绿', id: 3 } ]