写点什么

20 种数组去重的方法

作者:溪抱鱼
  • 2025-06-02
    河南
  • 本文字数:2598 字

    阅读完需:约 9 分钟

开始

本文有很多问题,并没有直接给出答案,大伙有自己思考的可以评论区留言。关于时间复杂度只是一个大体的估计。20种只能说保守了20种都是单论思路而已,暂时没想到更多的思路,有其他方法的可以评论区留言。

easy 模式

此时我们有一个极其简单的数组,它可能包含也不包含重复项。我们需要删除重复项并将唯一值放入新数组中。

const names = ["a","b","c","d","e","a","b"];
复制代码

new Set

时间复杂度:O(n^2), 但扩展符运算符耗费时间有点多,一般推荐

最简单的,new Set去重

let newNames = [...new Set(names)]
复制代码

new Set

时间复杂度:O(n^2), 比扩展运算符还费劲,一般推荐

let newNames = Array.from(new Set(names))
复制代码

new Map

时间复杂度:O(n^2), 一般推荐 通过new Map原型上的方法去重。

function dealArr (a) {  let newArr = []  let map = new Map()  for(let i = 0;i<a.length;i++){    if (!map.has(a[i])) {      map.set(a[i], true)      newArr.push(a[i])    }  };  return newArr}
复制代码

笨蛋双重 for 循坏

感觉实在没什么好说的,就纯暴力去重

function dealArr(a){    let len = a.length;    for(let i = 0; i < len; i++) for(let j = i + 1; j < len; j++)         if(a[j] == a[i]){            a.splice(j,1);            j--;            len--;        }    return a;}
复制代码


function dealArr(a) {  let b = [];  for (let i = a.length - 1; i >= 0; i--) {    for (let j = a.length - 1; j >= 0; j--) {      if (a[i] == a[j] && i != j) {        delete a[j];      }    }    if (a[i] != undefined) b.push(a[i]);  }  return b;}
复制代码

单 for 循坏

时间复杂度:O(n), 它真的太快了,它是所有种类的方法里最快的,大伙可以试一试, 推荐

for

循坏+hash查找

function dealArr(a) {    let obj = {};    let out = [];    let len = a.length;    let j = 0;    for(let i = 0; i < len; i++) {         let item = a[i];         if(obj[item] !== 1) {               obj[item] = 1;               out[j++] = item;         }    }    return out;}
复制代码

下面这种会快一点。

function dealArr(a) {  obj = {};  for (let i = 0; i < a.length; i++) {    obj[a[i]] = true;  }  return Object.keys(obj);}
复制代码

for and includes

时间复杂度:O(n^2), 不推荐

for

循环 + includes判断,includes会循坏到找到为止或者全部,所以挺慢的。

function dealArr(a) {    let newArr = [];    let j = 0;    for (i = 0; i < a.length; i++) {        let current = a[i];        if (!newArr.includes(current)) newArr[j++] = current;    }    return newArr;}
复制代码

for and indexOf

时间复杂度:O(n^2), 不推荐

for

循环 + indexof查找,indexOf会找到第一个为止或者全部。

function dealArr(a) {    let newArr = [];    let j = 0;    for (i = 0; i < a.length; i++) {        let current = a[i];        if (newArr.indexOf(current) < 0) newArr[j++] = current;    }    return newArr;}
复制代码

for and lastIndexOf

时间复杂度:O(n^2), 不推荐

没啥好说的,其实和indexOf一样只是正反序查找的区别而已,问就是慢

function dealArr(a) {    let newArr = [];    let j = 0;    for (i = 0; i < a.length; i++) {        let current = a[i];        if (newArr.lastIndexOf(current) < 0) newArr[j++] = current;    }    return newArr;}  
复制代码

for and newArr

相比哈希也慢

一个新数组和原数组对比,不同则放在新数组,最后返回。

function dealArr(a) {    let newArr = [a[0]];    for (let i = 1; i < a.length; i++) {        let repeat = false;        for (let j = 0; j < newArr.length; j++) {            if (a[i] === newArr[j]) {                repeat = true;                break;            }        }        if (!repeat) {            newArr.push(a[i]);        }    }    return newArr;}
复制代码

for and sort

想想有什么问题

先将原数组排序,再与相邻的进行比较,如果不同则存入新数组。

function dealArr(a) {    let formArr = a.sort()    let newArr=[formArr[0]]    for (let i = 1; i < formArr.length; i++) {        if (formArr[i]!==formArr[i-1]) newArr.push(formArr[i])    }    return newArr}
复制代码

splice

O(n^2),特别慢

function dealArr(arr) {    let i,j,len = arr.length;    for (i = 0; i < len; i++) {        for (j = i + 1; j < len; j++) {            if (arr[i] == arr[j]) {                arr.splice(j, 1);                len--;                j--;            }        }    }    return arr;}
复制代码

filter and indexOf

时间复杂度:O(n^2)一般推荐

filter

的本质相当于,在每一个元素上添加检查,检查该元素在数组中的第一个位置是否等于当前位置indexof是找到第一个符合条件的元素。重复元素在数组里的位置是与找到的第一个不同的。

let newNames = names.filter(function(item, index) {    return names.indexOf(item) == index;})
复制代码

但其实上述方法不是很好,因为可能你会操作到原数组,导致原数据变化,那么我们可以直接用filter的第三个参数来做这件事,保证原数据的不可变性。

let newNames = names.filter(function(item, index, self) {    return self.indexOf(item) == index;})
复制代码

filter and sort

时间复杂度:O(n)- O(n^2)不推荐

就是先对数组进行排序,然后删除与前一个元素相等的每个元素。大家也可以想想这方法有啥问题。提示:排序。

  let newNames =  a.sort().filter(function(item, index, self) {        return !index || item != self[index - 1];   });
复制代码

reduce

实在是太慢了,不推荐

reduce果然是js里最完美的api

let newNames = names.reduce(function(a,b){    if (a.indexOf(b) < 0 ) a.push(b);    return a;  },[]);
复制代码

笨蛋 hashMap

时间复杂度:O(n)一般

这个方法有点笨,通过哈希表查找fiter,大伙可以想一想缺陷是什么。(提示:对象,key。 测试用例: [1, '1']。)

function dealArr(a) {    let seen = {};    return a.filter(function(item) {        return seen.hasOwnProperty(item) ? false : (seen[item] = true);    });}
复制代码


用户头像

溪抱鱼

关注

还未添加个人签名 2025-02-09 加入

还未添加个人简介

评论

发布
暂无评论
20种数组去重的方法_JavaScript_溪抱鱼_InfoQ写作社区