本文最早宣布于csdn,为原创
通例要领两种
let json = arr => {
let res = [],
obj = {};
arr.forEach(value => {
let key = typeof(value) + value;
!obj.hasOwnProperty(key) && (res.push(value), obj[key] = 1);
})
return res;
}
let sort = arr => {
//数组深拷贝,为不了影响本来的数组
let newArr = arr.concat();
newArr.sort();
for (var i = newArr.length; i > 0; i--) {
if ( newArr[i] === newArr[ i - 1 ] ) { // use == if '2' eq 2, else ===
newArr.splice( i, 1 );
}
}
return newArr;
}
第一种要领经常运用但是有坑
console.log(unique([ new String(1), new Number(1) ]))
//[String]0: String0: "1"length: 1__proto__: String[[PrimitiveValue]]: "1"length: 1__proto__:Array[0]
遇到这类状况就出问题了
第二种要领运用sort
,sort
要领返回的效果并不一定是升序,重要目标是将反复的数字排到一同
运用ES5的indexOf
要领两种
let foreach = arr => {
arr.forEach(value => {
res.indexOf(value) == -1 && res.push(value);
}, res = [])
}
let unique = arr => {
let res = [];
arr.forEach(function(value) {
(res.indexOf(value) == -1) && res.push(value);
})
return res;
}
let arr = [1, 1, 2, 2];
unique3(arr);
console.log(res);
简约文雅版
let filter = arr => { return arr.filter(function (value, index, array) { return index <= array.indexOf(value);}); };
es6奇技淫巧
2016.7.7更新
看到批评提示的要领
let array = Array.from(new Set([1, 1, 1, 2, 3, 2, 4]));
console.log(array);
// => [1, 2, 3, 4]
补充申明,from要领如今浏览器支撑水平不太好,另外经测试,机能也不具有上风
机能对照
2016.7.12更新,近来发现了一篇文章举行机能测试,觉得很赞,今后测机能就用这个了
benchmark地点
let benchmark = require('benchmark');
let suit = new benchmark.Suite;
let arr = [1, 1, 1, 2, 3, 2, 4];
let es6 = arr => {
let array = Array.from(new Set(arr));
};
let filter = arr => {
arr.filter((value, index, array) => { return index <= array.indexOf(value);});
};
let json = arr => {
let res = [],
obj = {};
arr.forEach(value => {
let key = typeof(value) + value;
!obj.hasOwnProperty(key) && (res.push(value), obj[key] = 1);
})
return res;
}
let sort = arr => {
//数组深拷贝,为不了影响本来的数组
let newArr = arr.concat();
newArr.sort();
for (var i = newArr.length; i > 0; i--) {
if ( newArr[i] === newArr[ i - 1 ] ) { // use == if '2' eq 2, else ===
newArr.splice( i, 1 );
}
}
return newArr;
}
let foreach = arr => {
arr.forEach(value => {
res.indexOf(value) == -1 && res.push(value);
}, res = [])
}
suit.add('es6', function() {
es6(arr);
}).add('filter', function() {
filter(arr);
}).add('json', function() {
json(arr);
}).add('sort', function() {
sort(arr);
}).add('foreach', function() {
foreach(arr);
}).on('cycle', function(event) {
console.log(String(event.target));
}).on('complete', function() {
console.log('Fastest is ' + this.filter('fastest').map('name') + '\n slowest is ' + this.filter('slowest').map('name'));
}).run({'async': true});
在teminal运转node test.js获得以下效果
$ node 数组去重要领及对照.js
es6 x 275,353 ops/sec ±4.87% (63 runs sampled)
filter x 703,449 ops/sec ±1.49% (89 runs sampled)
json x 238,876 ops/sec ±5.24% (72 runs sampled)
sort x 217,857 ops/sec ±4.58% (64 runs sampled)
foreach x 915,368 ops/sec ±3.84% (65 runs sampled)
Fastest is foreach
slowest is sort
总结
以上一切要领都不会出现将1和”1″视作一同去重的状况,除开第一种,其他的要领也能区离开[new String(1), new Number(1)],这里的要领已经是比较全,和其他博客比起来只要一些完成上的差别,整体要领头脑是一样的
参考资料
一行代码完成数组去重(ES6)
从 JavaScript 数组去重谈机能优化
js对象的hasOwnProperty为何比数组的indexof要领在机能上高的多?
运用Benchmark.js和jsPerf剖析代码机能
源代码github地点