Map和Set都叫做集合,但是他们也有所不同。Set常被用来检查对象中是否存在某个键名,Map集合常被用来获取已存的信息。

Set

Set是有序列表,含有相互独立的非重复值。

创建Set

既然我们现在不知道Set长什么样,有什么价值,那么何不创建一个Set集合看看呢?

创建一个Set集合,你可以这样做:

let set = new Set();
console.log(set);//在浏览器控制台的输出结果
Set(0) {}size:(...)__proto__:Set[[Entries]]:Array(0)length:0

看起来像个对象,那么现在我们在控制台打印一个对象,对比一下两者有什么不同。

let obj = new Object()
console.log(obj)//在控制台输出对象
Object {}__proto__:

从输出结果看,Set和Object有明显的区别,反正他们就不是一个东西。

接着,我们看一下Set的原型有哪些:

这里主要介绍几个基础原型的作用,想要了解全部请前往 Set集合之家 查看:

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

Set.prototype.add(value)
在Set对象尾部添加一个元素。返回该Set对象。

Set.prototype.entries()
返回一个新的迭代器对象,该对象包含Set对象中的按插入顺序排列的所有元素的值的[value, value]数组。为了使这个方法和Map对象保持相似, 每个值的键和值相等。

Set.prototype.forEach(callbackFn[, thisArg])
按照插入顺序,为Set对象中的每一个值调用一次callBackFn。如果提供了thisArg参数,回调中的this会是这个参数。

Set.prototype.has(value)
返回一个布尔值,表示该值在Set中存在与否。

在例子中使用这几个方法测试一下:

let set = new Set();
set.add('haha');
set.add(Symbol('haha'));console.log(set.size); //2console.log(set);
Set(2) {"haha", Symbol(haha)}size:(...)__proto__:Set[[Entries]]:Array(2)0:"haha"1:Symbol(haha)length:2console.log(set.has('haha')) // true

到这里,你会发现Set像数组,又像一个对象,但又不完全是。

迭代Set

Set既然提供了entries和forEach方法,那么他就是可迭代的。

但如果你使用for in来迭代Set,你不能这样做:

for(let i in sets) {console.log(i); //不存在
}

for in迭代的是对象的key,而在Set中的元素没有key,使用for of来遍历

for(let value of sets) {console.log(value);
}
//"haha"
//Symbol(haha)//如果你需要key,则使用下面这种方法
for(let [key, value] of sets.entries()) {console.log(value, key);
}
//"haha" "haha"
//Symbol(haha) Symbol(haha)

forEach操作Set:Set本身没有key,而forEach方法中的key被设置成了元素本身。

sets.forEach((value, key) => {console.log(value, key);
});
//"haha" "haha"
//Symbol(haha) Symbol(haha)sets.forEach((value, key) => {console.log(Object.is(value, key));
});
//true true

Set和Array的转换

Set和数组太像了,Set集合的特点是没有key,没有下标,只有size和原型以及一个可迭代的不重复元素的类数组。既然这样,我们就可以把一个Set集合转换成数组,也可以把数组转换成Set。

//数组转换成Set
const arr = [1, 2, 2, '3', '3']
let set = new Set(arr);
console.log(set) // Set(3) {1, 2, "3"}//Set转换成数组
let set = new Set();
set.add(1);
set.add('2');
console.log(Array.from(set)) // (2) [1, "2"]

js面试中,经常会考的一道数组去重题目,就可以使用Set集合的不可重复性来处理。经测试只能去重下面3种类型的数据。

const arr = [1, 1, 'haha', 'haha', null, null]
let set = new Set(arr);
console.log(Array.from(set)) // [1, 'haha', null]
console.log([...set]) // [1, 'haha', null]

Weak Set集合

Set集合本身是强引用,只要new Set()实例化的引用存在,就不释放内存,这样一刀切肯定不好啊,比如你定义了一个DOM元素的Set集合,然后在某个js中引用了该实例,但是当页面关闭或者跳转时,你希望该引用应立即释放内存,Set不听话,那好,你还可以使用 Weak Set

语法:

new WeakSet([iterable]);

和Set的区别:

1、WeakSet 对象中只能存放对象值, 不能存放原始值, 而 Set 对象都可以.

2、WeakSet 对象中存储的对象值都是被弱引用的, 如果没有其他的变量或属性引用这个对象值, 则这个对象值会被当成垃圾回收掉. 正因为这样, WeakSet 对象是无法被枚举的, 没有办法拿到它包含的所有元素.

使用:

let set = new WeakSet();
const class_1 = {}, class_2 = {};
set.add(class_1);
set.add(class_2);
console.log(set) // WeakSet {Object {}, Object {}}
console.log(set.has(class_1)) // true
console.log(set.has(class_2)) // true

Map

Map是存储许多键值对的有序列表,key和value支持所有数据类型。

创建Map

如果说Set像数组,那么Map更像对象。而对象中的key只支持字符串,Map更加强大,支持所有数据类型,不管是数字、字符串、Symbol等。

// 一个空Map集合
let map = new Map()
console.log(map)

Map的所有原型方法:

对比Set集合的原型,Map集合的原型多了set()和get()方法,注意set()和Set集合不是一个东西。Map没有add,使用set()添加key,value,在Set集合中,使用add()添加value,没有key。

let map = new Map();
map.set('name', 'haha');
map.set('id', 10);
console.log(map)
// 输出结果
Map(2) {"name" => "haha", "id" => 10}size:(...)__proto__:Map[[Entries]]:Array(2)0:{"name" => "haha"}1:{"id" => 10}length:2console.log(map.get('id')) // 10
console.log(map.get('name')) // "haha"

使用对象做key

let map = new Map();
const key = {};
map.set(key, '谁知道这是个什么玩意');
console.log(map.get(key)) // 谁知道这是个什么玩意

Map同样可以使用forEach遍历key、value

let map = new Map();
const key = {};
map.set(key, '这是个什么玩意');
map.set('name', 'haha');
map.set('id', 1);
map.forEach((value, key) => {console.log(key, value)
})//Object {} "这是个什么玩意"
//"name" "haha"
//"id" 1

其他Map的使用方法可以前往 Map之家 学习。

Weak Map

有强Map,就有弱鸡Map。

和Set要解决的问题一样,希望不再引用Map的时候自动触发垃圾回收机制。那么,你就需要Weak Map。

let map = new WeakMap();
const key = document.querySelector('.header');
map.set(key, '这是个什么玩意');map.get(key) // "这是个什么玩意"//移除该元素
key.parentNode.removeChild(key);
key = null;

总结

Set集合可以用来过滤数组中重复的元素,只能通过has方法检测指定的值是否存在,或者是通过forEach处理每个值。

Weak Set集合存放对象的弱引用,当该对象的其他强引用被清除时,集合中的弱引用也会自动被垃圾回收机制回收,追踪成组的对象是该集合最好的使用方式。

Map集合通过set()添加键值对,通过get()获取键值,各种方法的使用查看文章教程,你可以把它看成是比Object更加强大的对象。

Weak Map集合只支持对象类型的key,所有key都是弱引用,当该对象的其他强引用被清除时,集合中的弱引用也会自动被垃圾回收机制回收,为那些实际使用与生命周期管理分离的对象添加额外信息是非常适合的使用方式。

记得刚开始学习JavaScript的时候,不知道各种数据类型有什么用,如果你现在刚学习Map和Set也是这种不知道能用来干什么的想法,那么,恭喜,他们已经开始走入你的编程生涯,慢慢的你就会熟悉他们。

=> 返回文章列表

《深入理解ES6》笔记——Set集合与Map集合(7)相关推荐

  1. Es6里面的Set和Map集合

    ECMAScript 6中的Set 集合 EcmAScript 6中新增了Set类型是一种有序列表,其中含有一些相互独立的非重复值,通过Set集合可以快速访问其中的数据,更有效地追踪各种离散值 创建S ...

  2. 笔记:Java中Map集合的基本功能及遍历方式

    Map集合概述: public interface Map<K,V> 将键映射到值的对象.不能包含重复的键; 每个键可以映射到最多一个值. 该接口代替了Dictionary类,它是一个完全 ...

  3. Java_Collection集合与Map集合的理解与应用

    集合 概述:可以存储多个数据的容器 集合和数组的区别: 相同点:都可以存储多个数组 不同点: 数组中可以存多个数据,但是不能自由的实现数据的新增和删除操作 集合中除了可以存储多个数据,还可以自由的实现 ...

  4. Java进阶(七)Set系列集合、Map集合体系

    七.Set系列集合.Map集合体系 需要学会什么? Set系列集合的特点:Set系列集合的特点和底层原理. 集合工具类Collections:快速的对集合进行元素的添加.排序等操作. 综合案例:把Co ...

  5. Java高级-Lambda 表达式、异常处理、集合、泛型、List集合、Map集合、Collections类

    目录 Lambda 表达式 Java Lambda 表达式的优缺点 异常处理 Exception 处理及常见异常 try catch语句 try catch finally语句 throws 声明异常 ...

  6. Java进阶,Set集合,Map集合

    Java进阶,Set集合,Map集合 一.Set系列集合 1.Set系列集系概述 Set系列集合特点 无序:存取顺序不一致 不重复:可以去除重复 无索引:没有带索引的方法,所以不能使用普通for循环遍 ...

  7. 集合 (二) ----- Map集合详解

    相关文章: <集合 (一) ----- 集合的基本概念与Collection集合详解> <集合 (二) ----- Map集合详解> 文章目录 Map集合详解 一.Map集合基 ...

  8. java进阶开发-----Set集合、Map集合(接java集合)

    (一).Set系列集合 Set系列集合特点 无序:存取顺序不一致 不重复:可以去除重复 无索引:没有带索引的方法,所以不能使用普通for循环遍历,也不能通过索引来获取元素. Set集合实现类特点 Ha ...

  9. ES6新特性(中)——ES6的集合(set集合、map集合等)

    这里写目录标题 ES6的集合 一.Set集合 1.操作方法 2.遍历方法: 二.WeakSet集合 1.概念理解 2.方法: 3.WeakSet 的应用场景/好处 三.Map集合 1.概念理解 2.属 ...

最新文章

  1. JGG :微生物所王军-综述固有免疫细胞在胃肠道疾病中研究进展
  2. Python运算符和编码
  3. php 文件写入磁盘错误,Linux磁盘读写故障的通常处理流程
  4. 老司机实战Windows Server Docker:3 单节点Windows Docker服务器简单运维(上)
  5. 使用C++的方式实现AES算法
  6. 优达学城深度学习之二——矩阵数学和Numpy复习
  7. rem适配的浏览器_移动端网页布局适配rem方案小结
  8. JAVA调用百度OCR实现身份证识别
  9. DOM元素节点属性outerHTML和innerHTML
  10. 富士施乐Fuji Xerox ApeosPort-IV 2060 驱动
  11. win10熄屏时间不对_win10系统屏幕熄屏时间的设置方法
  12. 乐理知识1--十二平均律
  13. ios sdk 穿山甲_Creator iOS接入穿山甲SDK
  14. fuchsia appmgr分析
  15. 如何正确选择注塑模具浇口位置?这下真的懂了
  16. iOS中 WGAFN_网络监控 技术分享
  17. 关于x86、x86-64、x64、i386、i486、i586和i686等名词的解释
  18. 难溶盐在盐酸中的溶解度分析
  19. 智能电视应用与移动应用开发的比较
  20. 华为od统一考试B卷【机器人走迷宫】Java 实现

热门文章

  1. 电脑桌面路径多了个计算机名,文件太多,电脑桌面太乱?一个技巧帮你解决!...
  2. 为什么重写equals一定要重写hashCode方法?
  3. python解释器的下载和安装
  4. 道德规范的心理学透视
  5. 规模 300+ 的研发团队,怎样保持工程高质高效?
  6. 实现不同vlan间PC不可互访,而不同vlan的PC均可访问服务器的特殊效果,(华为)...
  7. 任意进制转换简单理解
  8. MySQL5.6 主从复制配置
  9. 安装apache+gd2(jpeg,png等)+mysql-client+php脚本
  10. 去邵程程博客,得到很有喜感图片一张