- ES6 : Set
let ary = [12, 23, 12, 15, 25, 23, 25, 14, 16];
let arr = [...new Set(ary)] //使用展开运算符
let arr = Array.from(new Set(ary)) //使用Array.from
- 拿所有项和其后面的每一项进行对比,如果有重复的话就删除(最后一项不拿,因为其后面没有东西进行比较了)
let ary = [12, 23, 12, 15, 25, 23, 25, 14, 16];
for(let i = 0; i < ary.length - 1;i++){
let item = ary[i],
args = ary.slice(i+1); //取出除当前项之后的所有项为一个数组
if(args.indexOf(item)>-1){ //判断当前项是否在其后面数组项中存在;或者此处可以使用includes
//此处有两个思路:1、包含,将当前项删除 2、定义一个新数组将当前的不包含的放到新数组中,这样的话要遍历所有的包括最后一项
//删除方式一:splice(i,1);i--; //i--是为了解决删除后导致的数组塌陷问题
//使用splice删除会造成问题 1、原来数组改变,如果继续i++会造成数组塌陷问题 2、性能不好,一旦当前项删除,后面每一项的索引都要改变
//删除方式二:原来数组克隆一份一模一样的,之后在克隆数组中去删除
//删除方式三:赋值为null,之后过滤掉ary.filter(item=>item !== null)
// ary[i] = null;
//删除方式四:用最后一项替换,替换之后整个数组长度要减少1,并且替换过来后当前的替换项需要重新对比所以i--
ary[i] = ary[ary.length - 1]
ary.length--;
i--;
}
}
- 对象键值对方式(数组)
- 拿出一项放入空容器,如果已经存储过,删除当前项
let ary = [12, 23, 12, 15, 25, 23, 25, 14, 16];
let obj = {};
for(let i = 0;i<ary.length;i++){
let item = ary[i];
if(typeof obj[item] !== 'undefined'){ //对象中有这个属性,不存储
//此处对数组的操作跟上面的方式对数组的操作一样,都是讲最后一项替换到当前项
ary[i] = ary[ary.length - 1]
ary.length--;
i--;
continue;
}
obj[item] = item;
}
obj=null; //obj使用完之后,销毁掉当前使用的堆
- 先排序,再相邻比较
- 相邻项处理方案
let ary = [12, 23, 12, 15, 25, 23, 25, 14, 16];
ary.sort((a,b)=>a-b) //升序排序
//方式一:每一项和后一项进行比较,如果相同就删除当前项。最后一项没有后一项,所以不用
for(let i = 0;i<ary.length-1;i++){
if(ary[i] === ary[i+1]){
ary.splice(i,1);
ary.length--;
i--;
}
}
//方式二:可以使用正则
ary = ary.join('@')+'@' //"12@12@14@15@16@23@23@25@25@"
let reg = /\d+@\1*/g // \d拿到数字。 \d+@ 拿到数字加上@符号
let arr = []
ary.replace(reg,(val,group1)=>{
arr.push(Number(group1.slice(0,group1.length-1) ))
})
conole.log(arr)
数组去重经典的四大方案:
使用ES6的Set方案
前一项跟后面每一项进行比较
- 使用空容器存储验证是否存过
- 相邻项方案