set

实例属性

Set.prototype.size返回 Set 对象中的值的个数

实例方法

Set.prototype.add(value)在Set对象尾部添加一个元素。返回该Set对象。
Set.prototype.clear()移除Set对象内的所有元素。
Set.prototype.delete(value)移除Set中与这个值相等的元素,如果该元素存在,返回true,否则返回false。
Set.prototype.forEach(callbackFn[, thisArg])为每个值调用callBackFn。若提供thisArg,会替换回调中的this。
Set.prototype.has(value)返回一个布尔值,表示该值在Set中存在与否。
Set.prototype.keys()返回一个新的迭代器对象,该对象包含Set对象中的按插入顺序排列的所有元素的键。
Set.prototype.values()返回一个新的迭代器对象,该对象包含Set对象中的按插入顺序排列的所有元素的值。
Set.prototype.entries()返回一个新的迭代器对象,该对象包含Set对象中的按插入顺序排列的所有元素的值的[value, value]数组。为了使这个方法和Map对象保持相似, 每个值的键和值相等。
Set.prototype@@iterator返回一个新的迭代器对象,该对象包含Set对象中的按插入顺序排列的所有元素的值。

与数组的差别

不能有相同的值

  1. // Set 数据结构
  2. const s = new Set()
  3. s.add(1).add(2).add(3).add(4).add(2)
  4. // console.log(s)
  5. // s.forEach(i => console.log(i))
  6. // for (let i of s) {
  7. // console.log(i)
  8. // }
  9. // console.log(s.size)
  10. // console.log(s.has(100))
  11. // console.log(s.delete(3))
  12. // console.log(s)
  13. // s.clear()
  14. // console.log(s)

应用场景

  1. // 应用场景:数组去重
  2. const arr = [1, 2, 1, 3, 4, 1]
  3. // const result = Array.from(new Set(arr))
  4. const result = [...new Set(arr)]
  5. console.log(result)
  6. // 弱引用版本 WeakSet
  7. // 差异就是 Set 中会对所使用到的数据产生引用
  8. // 即便这个数据在外面被消耗,但是由于 Set 引用了这个数据,所以依然不会回收
  9. // 而 WeakSet 的特点就是不会产生引用,
  10. // 一旦数据销毁,就可以被回收,所以不会产生内存泄漏问题。

map

实例属性

Map.prototype.size返回Map对象的键/值对的数量。

实例方法

Map.prototype.clear()移除Map对象的所有键/值对 。
Map.prototype.delete(key)如果 Map 对象中存在该元素,则移除它并返回 true;否则如果该元素不存在则返回 false。
Map.prototype.forEach(callbackFn[, thisArg])为 Map对象里的每一键值对调用一次callbackFn函数。如果为forEach提供了thisArg,它将在每次回调中作为this值。
Map.prototype.get(key)返回键对应的值,如果不存在,则返回undefined。
Map.prototype.has(key)返回一个布尔值,表示Map实例是否包含键对应的值。
Map.prototype.keys()返回一个新的 Iterator对象, 它按插入顺序包含了Map对象中每个元素的键 。
Map.prototype.set(key, value)设置Map对象中键的值。返回该Map对象。
Map.prototype.values()返回一个新的Iterator对象,它按插入顺序包含了Map对象中每个元素的值 。
Map.prototype.entries()返回一个新的 Iterator 对象,它按插入顺序包含了Map对象中每个元素的 [key, value] 数组。
Map.prototype@@iterator和entries()一样。

与对象的差别

1.意外的键
Map 默认情况不包含任何键。只包含显式插入的键。
一个 Object 有一个原型, 原型链上的键名有可能和你自己在对象上的设置的键名产生冲突。注意: 虽然 ES5 开始可以用 Object.create(null) 来创建一个没有原型的对象,但是这种用法不太常见。
2.键的类型
一个 Map的键可以是任意值,包括函数、对象或任意基本类型。
一个Object 的键必须是一个 String 或是Symbol。
3.键的顺序
Map 中的 key 是有序的。因此,当迭代的时候,一个 Map 对象以插入的顺序返回键值。
一个 Object 的键是无序的。注意:自ECMAScript 2015规范以来,对象确实保留了字符串和Symbol键的创建顺序; 因此,在只有字符串键的对象上进行迭代将按插入顺序产生键。
4.Size
Map 的键值对个数可以轻易地通过size 属性获取
Object 的键值对个数只能手动计算
5.迭代
Map 是 iterable 的,所以可以直接被迭代。
迭代一个Object需要以某种方式获取它的键然后才能迭代。
6.性能
Map在频繁增删键值对的场景下表现更好。
Object在频繁添加和删除键值对的场景下未作出优化。

  1. // Map 数据结构
  2. // const obj = {}
  3. // obj[true] = 'value'
  4. // obj[123] = 'value'
  5. // obj[{ a: 1 }] = 'value'
  6. // console.log(Object.keys(obj))
  7. // console.log(obj['[object Object]'])
  8. const m = new Map()
  9. const tom = { name: 'tom' }
  10. m.set(tom, 90)
  11. console.log(m)
  12. console.log(m.get(tom))
  13. // m.has()
  14. // m.delete()
  15. // m.clear()
  16. m.forEach((value, key) => {
  17. console.log(value, key)
  18. })
  19. // 弱引用版本 WeakMap
  20. // 差异就是 Map 中会对所使用到的数据产生引用
  21. // 即便这个数据在外面被消耗,但是由于 Map 引用了这个数据,所以依然不会回收
  22. // 而 WeakMap 的特点就是不会产生引用,
  23. // 一旦数据销毁,就可以被回收,所以不会产生内存泄漏问题。