在数据处理中,数组去重是一个高频操作。无论是清理用户输入,还是聚合数据,我们经常需要从数组中移除重复的元素。JavaScript提供了多种方法来实现这个目标,每种方法在简洁性、效率和适用场景上各有侧重。
![图片[1]-如何实现数组去重?-速码派](http://www.sumapai.com/wp-content/uploads/2026/01/5e99d2fdd0e34f68ab19cef5c433cfc4tplv-tb4s082cfz-aigc_resize_1080_1080-1-1024x683.webp)
利用Set数据结构的唯一性
ES6引入的Set对象是最简洁的现代解决方案。Set本身只存储唯一值,将数组转为Set后再转回数组,即可自动去除所有重复项。
const arr = [1, 2, 2, 3, 4, 4, 5];
const uniqueArr = [...new Set(arr)];
console.log(uniqueArr);
这种方法代码量极少,语义清晰。但它无法区分NaN(在Set中,NaN被视为等于自身),且会忽略对象之间的差异(因为每个对象引用都是唯一的)。
使用filter与indexOf的经典组合
在ES6之前,一种常见的方法是利用filter方法配合indexOf来检查每个元素是否是其第一次出现的位置。
const arr = ['a', 'b', 'a', 'c', 'b'];
const uniqueArr = arr.filter((item, index, array) => {
return array.indexOf(item) === index;
});
console.log(uniqueArr);
其原理是:indexOf总是返回第一个匹配项的索引。如果当前元素的索引与其第一次出现的索引相同,则说明它是第一次出现,应被保留。这种方法可以处理NaN吗?不行,因为indexOf无法正确找到NaN。
使用reduce构建新数组
reduce方法也适合用于累积一个不包含重复项的新数组。它提供了更灵活的控制,适合在去重过程中加入更复杂的逻辑。
const arr = [1, 2, 2, 3, 3, 3];
const uniqueArr = arr.reduce((acc, current) => {
if (!acc.includes(current)) {
acc.push(current);
}
return acc;
}, []);
console.log(uniqueArr);
reduce通过一个累加器acc(初始为空数组)遍历原数组,如果当前元素不在累加器中,就将其加入。这种方式直观但效率可能不是最高,因为对每个元素都要调用includes进行检查。
针对对象数组的去重
当数组元素是对象时,上述基于值比较的方法通常无效。这时需要根据对象的特定属性来判断是否重复。
const users = [
{id: 1, name: 'Alice'},
{id: 2, name: 'Bob'},
{id: 1, name: 'Alice'}
];
const uniqueUsers = [];
const seenIds = new Set();
for (const user of users) {
if (!seenIds.has(user.id)) {
seenIds.add(user.id);
uniqueUsers.push(user);
}
}
console.log(uniqueUsers);
这里我们使用一个Set来记录已经出现过的id,从而确保id唯一。这种方法可以推广到任何需要根据特定规则去重的场景。
选择哪种方法取决于你的具体需求。对于包含基本类型的简单数组,[...new Set(arr)]是不二之选。如果需要兼容旧环境或处理复杂对象,则可以考虑filter、reduce或手动的循环检查。理解每种方法的原理,能帮助你在不同场景下做出最合适的选择。




















暂无评论内容