数组去重常见方法 js

数组去重是面试常见的题目,要么口述要么手写,也算较为简单的一道题目,但却有多种方法解答。不过在实际开发中,数据一般都被后端处理过了,到了前端这里数据很少 有需要去重的情况。
这里我们统一测试数据和调用方法如下:

var arr = [1,12,1,"asa","asb","as",NaN,NaN,undefined,null,null,undefined,"NaN","undefined","null","null","Nan","undefined",true,true,false,false,"true","false","true","false",{},{},{name:1},{name:1}];
unique(arr);  

1.Es6新方法(Set去重)
无法对{}数据去重

function unique(arr){
	return Array.from(new Set(arr));
}
// 结果: [1, 12, "asa", "asb", "as", NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

可利用“…”扩展运算符简化该方法。
无法对{}数据去重

function unique(arr){
	return [...new Set(arr)];
}
// 结果:[1, 12, "asa", "asb", "as", NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

2.遍历数组使用indexOf()方法
这里遍历数组使用for,for…in,for…of,forEach都行,但要注意for…in是遍历下标。
无法对NaN和{}数据去重

function unique(arr){
	var newArr = [];
	arr.forEach(ele=>{
		if(newArr.indexOf(ele) == -1){
			newArr.push(ele);
		}
	})
	return newArr;
}
// 结果:[1, 12, "asa", "asb", "as", NaN, NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

3.遍历数组使用includes()方法
无法对{}去重

function unique(arr){
	var newArr = [];
	arr.forEach(ele=>{
		if(!newArr.includes(ele)){
			newArr.push(ele);
		}
	})
	return newArr;
}
// 结果:[1, 12, "asa", "asb", "as", NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

4.利用filter鉴别出现位置和下标相等过滤
原理:在数组中首次出现的位置和下标相同则过滤出来
无法对NaN和{}去重,且NaN消失。

function unique(arr){
	return arr.filter((item,index) => {
		return arr.indexOf(item) == index; 
	})
}
// 结果:[1, 12, "asa", "asb", "as", undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

5.利用对象Key值过滤
原理:利用的是对象的key值不能相同,最后输出key值。需要注意的是如果直接输出key值其类型均为字符串,如果这种结果不是你想要的,可以定义一个空数组,每次if执行时存取值。
NaN可去重,但是非字符串值会当作字符串值对待(NaN等同于"NaN"、true等同于"true")。

function unique(arr){
	var obj = {};
	arr.forEach(ele => {
		if(!obj[ele]){
			obj[ele]=1;
		}
	})
	return Object.keys(obj);
}
// 结果:["1", "12", "asa", "asb", "as", "NaN", "undefined", "null", "Nan", "true", "false", "[object Object]"]

6.使用ES6的Map去重与方法5类似
无法对{}去重

function unique(arr){
	let map = new Map();
	let newArr = new Array();
	arr.forEach(ele => {
		if(map.has(ele)){
			map.set(ele, 1);
		}else{
			map.set(ele, 0);
			newArr.push(ele);
		}
	})
	return newArr;
}
// 结果:[1, 12, "12", "asa", "asb", "as", NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

7.使用reduce()配合includes()去重,与上面遍历配合inclues()类同。
无法对{}去重
reduce()方法使用的不多,这里介绍一下:

用法:array.reduce(function(total, currentValue, currentIndex, arr), initialValue)
参数:

total 必需。初始值, 或者计算结束后的返回值。
currentValue 必需。当前元素
currentIndex 可选。当前元素的索引
arr 可选。当前元素所属的数组对象。
initialValue 可选。传递给函数的初始值

结果:返回total

function unique(arr){
	return arr.reduce(function(total, current){
		return total.includes(current) ? total : [...total, current];
	},[]);  // 初始值为空数组
}
// 结果:[1, 12, "12", "asa", "asb", "as", NaN, undefined, null, "NaN", "undefined", "null", "Nan", true, false, "true", "false", {…}, {…}, {…}, {…}]

其他方法与以上几种类同,这里不再做其他演变。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值