Set 简介
ES6 新增了数据结构 Set,与数组类似,特征如下:
- 无序
- 元素不能重复
Set 集合和 Array 数组的区别
- Set 元素不能重复,Array 元素可以重复
- Set 是无序结构,操作很快,Array 是有序结构,操作很慢
- Set 没有下标的概念,无法通过下标读取元素,Array 可以通过下标读取元素
- 操作 Set 的 API 和 Array 不同
Set 的基本操作
大部分 API 和 Map 相同
new —— 创建 Set
// 创建空集合 const s = new Set(); // 创建时赋值 const colors = new Set(['red',white,'blue']);
也可传入数组创建set,但若数组内存在相同元素,则会去重!
let list = [1, 2, 3, 3]; let my_set = new Set(list); console.log(my_set); // 打印 Set(3) { 1, 2, 3 }
注意:引用类型的数据地址不同,即便看起来值一样,也属于不同的数据!
let list = [ { name: "朝阳", }, { name: "朝阳", }, ]; let my_set = new Set(list); console.log(my_set); // Set(2) { { name: '朝阳' }, { name: '朝阳' } }
add —— 添加元素
my_set.add(1)
若原 set 中已存在新添加的元素,则什么都不会发生,也不会报错。
delete —— 删除元素
my_set.delete(1)
若原 set 中不存在要删除的元素,则什么都不会发生,也不会报错。
数组中基于元素的索引 splice() 来删除元素,速度很慢。
clear —— 清空元素
my_set.clear()
has—— 查询是否存在目标元素
返回 true / false
if (my_set.has("name")) { }
- 数组中使用 indexOf() 或 includes() 查询是否存在目标元素是比较慢。
- 数组无法使用 indexOf() 或 includes() 来查找 NaN
let list = [NaN, 1, 3]; let index = list.indexOf(NaN); console.log(index); // 得到 -1
- Set 可以通过 has 查找 NaN
let my_set = new Set([NaN, 2, 3]); console.log(my_set.has(NaN)); // 得到 true
size —— 获取元素的数量
类似数组的 .length
my_set.size
遍历 Set
// 没有 index my_set.forEach((val) => { console.log(val); });
Set 的性能(与 Array 对比)
- Set用于搜索、删除和插入元素的方法的时间复杂度都只有 O(1),即数据的大小实际上与这些方法的运行时间无关。
- 数组搜索的时间复杂度为 O(N),运行时间的增长速度与数据大小的增长速度相同。
Set 的应用场景
Vue3 数据响应式 reactive 和 effect 的源码中,大量使用了 Set
数组去重
仅适用于简单数组
let oldList = [1, 2, 3, 3]; let newList = Array.from(new Set(oldList)); // 得到 [1, 2, 3]
或
let arr = [3, 5, 2, 2, 5, 5]; let unique = [...new Set(arr)]; // [3, 5, 2]
提升数组类数据的操作性能
因 Set 操作数据的性能比 Array 好,当需要对数据进行频繁操作,且对数据顺序无需求时,可考虑改用 Set 提升性能!