MapES6
是一个 <键-值> 对的集合,类似对象,但是 key 可以是任意类型。一个 key 只能对应一个 value,对一个 key 多次放入 value,后面的值会覆盖前面的值。
使用
// 创建 map
let m = new Map([
['a', 1],
['b', 2],
['c', 3],
])
m.size // 返回元素个数
m.set('d', 4) // 根据键存储值
m.get('a') // 根据键来返回值,如果 map 中不存在对应的 key,则返回 undefined
m.delete('b') // 删除指定键的值,如果 map 中的元素存在并已被移除,则为 true,否则为 false
m.has('c') // 如果 key 存在则返回 true,否则返回 false
m.clear() // 清空 map,返回 undefined
迭代
map.keys()
:包含所有键的可迭代对象map.values()
:包含所有值的可迭代对象map.entries()
:包含所有实体[key, value]
的可迭代对象,for..of
默认使用这个map.forEach()
:对 map 的每个键/值对执行一次提供的函数for...of
:遍历 entries
与对象转换
- Object ⇒ Map:
let map = new Map( Object.entries(obj) )
- Map ⇒ Object:
let obj = Object.fromEntries( map.entries() )
Map 使用 SameValueZero 算法来比较键是否相等
为何有了 object
还要有 map
?
object | map |
---|---|
key 只能是字符串 | key 可以是任意类型 |
不可迭代 | 可迭代 |
无序 | 有序 |
SetES6
是一个 <值> 的集合,类似数组,但是成员的值都是唯一的没有重复,也不能直接按下标来获取元素
使用
let s = new Set([1, 2, 3]) // 创建 Set
s.size // 返回元素个数
s.add(4) // 添加一个值
s.delete(4) // 删除值,如果 value 在这个方法调用的时候存在则返回 true ,否则返回 false
s.has(1) // 如果 value 在 set 中,返回 true,否则返回 false
s.clear() // 清空 set,返回 undefined
迭代
set.keys()
:包含所有值的可迭代对象set.values()
:同上,为了兼容 Mapset.entries()
:包含所有的实体[value, value]
的可迭代对象,为了兼容 Mapset.forEach()
:对 set 的每个值执行一次提供的函数for...of
:遍历所有值
NOTE
相同点
- Map 和 Set 都是有序的,都按照插入顺序进行迭代
- Map 和 Set 的添加元素方法返回的都是其本身,所以可以链式调用
WeakMap / WeakSetES6
由于 垃圾回收 机制,Map 和 Set 中的对象不会被回收。但是 WeakMap 中的 对象key 或者 WeakSet 中的 对象值,如果没有其他的变量也指向该对象,则会被垃圾回收
WeakMap
和 WeakSet
的出现,就是为了不阻止对象被垃圾回收,所以 WeakMap
的 key 只能是 对象,WeakSet
中也只能添加 对象
由于垃圾回收的时机无法确定,即内部元素随时可能消失。所以它们不支持迭代也没有 keys(),values() 和 entries() 方法
- WeakMap 只有:
get
,set
,delete
,has
- WeakSet 只有:
add
,delete
,has
Note
主要应用场景是额外数据的存储,当源数据被删除时,自动跟着一起被删除
WeakMap 支持 Symbol 作为 keyES2023