Map和WeakMap的方法和区别
Map
Map
是一组键值对的结构,具有极快的查找速度。
一、构造函数不同
let map = new Map(); let weakmap = new WeakMap();
二、内置函数不同
- Map的API有:
(1) Map.prototype.clear()
(2) Map.prototype.delete()
(3) Map.prototype.entries()
(4) Map.prototype.forEach()
(5) Map.prototype.get()
(6) Map.prototype.has()
(7) Map.prototype.keys()
(8) Map.prototype.set()
(9) Map.prototype.values()
(10) Map.prototype[@@iterator]()
- WeakMap的API有:
(1) WeakMap.prototype.delete()
(2) WeakMap.prototype.get()
(3) WeakMap.prototype.has()
(4) WeakMap.prototype.set()
可以看出weakMap api少了clear, entries,forEach,keys,values,以及获取iterator对象的方法,另外weakMap还没有size属性,无法获取内部存了多少个映射。
三、GC垃圾回收
let a = {x: 12}; let b = {y: 13}; let map = new Map(); let weakMap = new WeakMap(); map.set(a, '14'); weakMap.set(b, '15'); a = null; b = null; // 设置为null提醒垃圾回收可以回收了。
当把a, b都设置成null之后,GC会回收weakMap中的b对象对应的键值对(这里的意思是键和值都回收),也就是
{ y: 13}
这个对象会被回收,'14'
这个常量也会被清除。但是不会回收Map中a对象对应的键值对,也就是{x: 12}
这个对象并不会回收。WeakMap
中值被回收,是因为键被回收了let a = {x: 12}; let b = {y: 15}; let weakMap = new WeakMap(); weakMap.set(a, b); console.log(weakMap.get(a)); b = null; // 这样做不会影响weakMap的存储 console.log(weakMap.get(a));
如果是WeakMap
的话,target
和obj
存在的就是弱引用关系,当下一次垃圾回收机制执行时,这块内存就会被释放掉。设想一下,如果我们要拷贝的对象非常庞大时,使用Map
会对内存造成非常大的额外消耗,而且我们需要手动清除Map
的属性才能释放这块内存,而WeakMap
会帮我们巧妙化解这个问题。