map,wekmap以及set ,wekset的区别
首先我们来看一下整体的区别:
Map——本质上是键值对的集合,类似集合;可以遍历,方法很多,可以跟各
种数据格式转换。
WeakMap——只接受对象最为键名(null 除外),不接受其他类型的值作为键
名;键名是弱引用,键值可以是任意的,键名所指向的对象可以被垃圾回收,
此时键名是无效的,但是要注意,键值是被键名引用的,不可以被垃圾回收机制会回收的;不能遍历,方法有 get、set、has、delete。
Set——对象允许你存储任何类型的唯一值,无论是原始值或者是对象引用
WeakSet——成员都是对象;成员都是弱引用,可以被垃圾回收机制回收,可以用来保存 DOM 节点,不容易造成内存泄漏;
Map我们在使用的过程中,我们是经常会去拿map和object来比较,在一般情况下二者的使用是差不多的,但是也会存在以下的几点区别:
1 Object只能使用数值、字符串或符号作为键不同,Map可以使用任何JavaScript数据类型作为键。
const m = new Map();
const functionKey = function() {};
const symbolKey = Symbol();
const objectKey = new Object();
m.set(functionKey, "functionValue");
m.set(symbolKey, "symbolValue");
m.set(objectKey, "objectValue");
alert(m.get(functionKey)); // functionValue
alert(m.get(symbolKey)); // symbolValue
alert(m.get(objectKey)); // objectValue
// SameValueZero比较意味着独立 实例不冲突
alert(m.get(function() {})); // undefined
2 内存占用:相同内存map相对object能多存储大约50%的键值对。
3 插入性能:map大多数时候更快一些。
4 查找性能:object某些情况下更快一些。
5 删除性能:object的删除性能比较差,而map的删除性能相对更快。
这两者的插入和查找速度都不会随着数据量增多而线性改变。整体上来说的话是map更有优势,在代码的处理逻辑中我们可以按以上的优势来进行对应的处理。优化代码性能。
wekmap 是map的“兄弟”,是一种弱映射,主要区别体现在能否被垃圾回收机制回收。
弱映射中的键只能是Object或者继承自Object的类型,尝试使用非对象设置键会抛出TypeError。值的类型没有限制。
下面我们来看一下引用的情况:
const weak = new WeakMap();
weak.set({}, "val");
set()方法初始化了一个新对象并将它用作一个字符串的键。因为没有指向这个对象的其他引用,所以当这行代码执行完成后,这个对象键就会被当作垃圾回收。然后,这个键/值对就从弱映射中消失了,使其成为一个空映射。在这个例子中,因为值也没有被引用,所以这对键/值被破坏以后,值本身也会成为垃圾回收的目标。
Wekmap使用场景:
1 私有变量:
弱映射造就了在JavaScript中实现真正私有变量的一种新方式。前提很明确:私有变量会存储在弱映射中,以对象实例为键,以私有成员的字典为值。
2 DOM节点数据:
因为WeakMap实例不会妨碍垃圾回收,所以非常适合保存关联元数据。
const domLogin = new Map();
const loginButton = document.querySelector('#login');
// 给这个节点关联一些元数据
domLogin.set(loginButton, {disabled: true});
假设在上面的代码执行后,页面被JavaScript改变了,原来的登录按钮从DOM树中被删掉了。但由于映射中还保存着按钮的引用,所以对应的DOM节点仍然会逗留在内存中,除非明确将其从映射中删除或者等到映射本身被销毁。
如果这里使用的是弱映射,如以下代码所示,那么当节点从DOM树中被删除后,垃圾回收程序就可以立即释放其内存(假设没有其他地方引用这个对象):
const domLogin = new WeakMap();
const loginButton = document.querySelector('#login');
// 给这个节点关联一些元数据
domLogin.set(loginButton, {disabled: true});
对于set和wekset其实和map与wekmap的性质是一样的,wekset也是set的弱引用,也就是能被垃圾回收机制去回收掉,这就是wek这个单词所体现的弱的地方,具体的这里就不在赘述了,如果对于以上还不是很了解的,可以去MDN再细看一下。