javascript set 高效去重的核心是底层哈希表实现与 samevaluezero 算法:查找/插入/删除平均 o(1),自动去重,支持 nan 和 ±0 同值判定,保留插入顺序,但对象按引用比较。

JavaScript 中 Set 实现高效去重,核心在于它底层使用哈希表(Hash Table)做键值存储,查找、插入、删除平均时间复杂度都是 O(1),且自动忽略重复值——你只管添加,它自己判断是否存在。
Set 的去重机制:基于 SameValueZero 比较
Set 判断是否重复,用的是 SameValueZero 算法(和 === 基本一致,但特别处理 +0 和 -0 视为相等,NaN 也视为和自身相等)。这意味着:
-
new Set([1, 1, 2, 2])→{1, 2} -
new Set([0, -0, NaN, NaN])→{0, NaN}(不是{0, -0, NaN}) - 对象或函数即使内容相同,也被视为不同引用:
new Set([{a:1}, {a:1}])→ 两个元素都保留
常见去重写法:简洁又高效
相比手写循环+数组 includes()(O(n²)),Set 一行搞定:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- 数组去重:
[...new Set(arr)]或Array.from(new Set(arr)) - 字符串去重(字符级):
[...new Set('abac')].join('')→'abc' - 对象数组按某字段去重(需配合
Map或额外逻辑,Set本身不支持)
为什么比数组 filter + indexOf 更快?
手动去重常写成:arr.filter((item, i) => arr.indexOf(item) === i)。问题在于每次 indexOf 都要遍历前面部分,总时间接近 O(n²);而 Set 每次 add() 内部只需一次哈希计算和桶查找,整体是 O(n)。数据量稍大(比如上万项),差距就很明显。
注意边界:Set 不是万能去重器
Set 高效,但有它的适用前提:
- 只适合基础类型或需要引用唯一性的场景;深层对象去重得靠
JSON.stringify(有局限)或自定义 key 生成逻辑 - 不保持原始顺序?不会——
Set是有序结构,插入顺序即迭代顺序(ES2015+ 规范保证) - 内存略高:每个值都要存一份引用,不过对大多数前端场景影响极小
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










