ES6新增的Map和WeakMap 又是什么玩意?非常详细的解释
上一篇文章讲了set和weakSet,这节咱就讲Map和weakMap是什么?这两篇文章并没有什么联系,主要知识用法类似而已.嘿嘿,是不是感觉舒服多了.
什么是Map
介绍什么是Map,就不得不说起Object对象,我们都知道Object对象是键值对的集合:
- //Object对象
- {"name":"前端君","gender":1}
ES5中的key键名的类型要求一定是字符串,当然,ES6已经允许属性名的类型是Symbol,前面的文章有所讲解
现在,ES6 提供了Map结构给我们使用,它跟Object对象很像,但是不同的是,它的key键名的类型不再局限于字符串类型了,它可以是各种类型的值;可以说,它比Object对象更加灵活了,当然,也更加复杂了。
Map的基本用法
知道了什么是Map,我们接着来学学它的基本用法,看看它是怎么使用的。
Map结构提供了一个构造函数给我们,我们使用的时候需要用new来创建实例:
- let m = new Map();
如果想要在创建实例的同时,初始化它的内容,我们可以给它传参,形式跟Set结构类型,都是需要用数组作为参数,我们来试试看看:
- let m = new Map([
- ["name","前端君"],
- ["gender",1]
- ]);
- console.log(m);
- //打印结果:Map {"name" => "前端君", "gender" => 1}
大家注意Map( )方法里面的参数,首先它是一个数组,而里面的内容也是由多个数组组成,“name”:“前端君”作为一个键值对,将它们装在一个数组里面,[“name”:“前端君”],另外一组键值对也一样:[“gender”:1 ]。这就是初始化一个Map结构实例的基本写法。
初始化成实例后,Map结构还提供了一些实例的属性和方法供我们实现对实例的操作。我们一起看看都有哪些属性和方法。
set( )方法
set( )方法作用:给实例设置一对键值对,返回map实例。
- let m = new Map();
- //set方法添加
- //添加一个string类型的键名
- m.set("name","前端君");
- //添加一个数字类型的键名
- m.set(1,2);
- console.log(m);
- //打印结果:Map {"name" => "前端君", 1 => 2}
set方法的使用很简单,只需要给方法传入key和value作为键名和键值即可。注意:第三行代码中,我们传入的key是数字1,这就证明了,Map结构确实可以存储非字符串类型的键名,当然你还可以设置更多其它类型的键名,比如:
- //数组类型的键名
- m.set([1],2);
- //对象类型的键名
- m.set({"name":"Zhangsan"},2);
- //布尔类型的键名
- m.set(true,2);
- //Symbol类型的键名
- m.set(Symbol('name'),2);
- //null为键名
- m.set(null,2);
- //undefined为键名
- m.set(undefined,2);
以上6种类型值都可以作为键名,可以成功添加键值对,没毛病。
使用set方法的时候有一点需要注意,如果你设置一个已经存在的键名,那么后面的键值会覆盖前面的键值。我们演示一下:
- let m = new Map();
- m.set("name","前端君");
- console.log(m);
- //结果:Map {"name" => "前端君"}
- //再次设置name的值
- m.set("name","隔壁老王");
- console.log(m);
- //结果:Map {"name" => "隔壁老王"}
上面的案例,我们第一次把name的值设置为“前端君”,当再次使用set方法设置name的值的时候,后者成功覆盖了前者的值,从此“前端君” 变 “隔壁老王”。
get( )方法
get( )方法作用:获取指定键名的键值,返回键值。
- let m = new Map([["name","前端君"]]);
- m.get("name");//结果:前端君
- m.get("gender");//结果:undefined
get方法使用也很简单,只需要指定键名即可。获取存在对应的键值,如果键值对存在,就会返回键值;否则,返回undefined,这个也很好理解。
delete( )方法
delete( )方法作用:删除指定的键值对,删除成功返回:true,否则返回:false。
- let m = new Map();
- m.set("name","前端君");
- //结果:Map {"name" => "前端君"}
- m.delete("name");//结果:true
- m.delete("gender");//结果:false
我们使用delete方法,删除“name”的时候成功,返回了true。删除“gender”的时候,由于Map结构中不存在键名:“gender”,所以删除失败,返回false。
clear( )方法
跟Set结构一样,Map结构也提供了clear( )方法,让你一次性删除所有键值对。
- let m = new Map();
- m.set("name","前端君");
- m.set("gender",1);
- m.clear();
- console.log(m);
- //打印结果:Map {}
使用clear方法后,我们再打印一下变量m,发现什么都没有,一个空的Map结构,说明clear方法起作用了。
has( )方法
has( )方法作用:判断Map实例内是否含有指定的键值对,有就返回:true,否则返回:false。
- let m = new Map();
- m.set("name","前端君");
- m.has('name');//结果:true
- m.has('age');//结果:false
Map实例中含有键名:name,就返回了true,键名age不存在,就返回false。好理解吧,比较简单。
可遍历
Object对象能被for...in遍历,Map结构也不示弱,同样可以被遍历。我们可以使用ES6的新特性for...of来遍历它的键名或者键值。
entries( )方法
entries( )方法作用:返回实例的键值对遍历器。
我们在第十三节说过,for...of可以遍历具有遍历器接口的对象。那么,我们就结合for...of来演示一下Map结构的遍历。
- let m = new Map([
- ["name","前端君"],
- ["age",25]
- ]);
- for(let [key,value] of m.entries()){
- console.log(key+' '+value);
- }
- //打印结果:name 前端君
- // age 25
案例中的 m.entries( ) 返回键值对的遍历器,使用了for...of来遍历这个遍历器,得到的值分别赋值到key和value,然后控制台分别输出它们。
还记得吗?上一节中,介绍Set结构的遍历的时候,也是这样的遍历方式。
keys( ) 和 values( ) 方法
keys( )方法:返回实例所有键名的遍历器。
values( ) 方法:返回实例所有键值的遍历器。
既然都是遍历器,那就用for...of把它们遍历出来吧:
- let m = new Map([
- ["name","前端君"],
- ["age",25]
- ]);
- //使用keys方法获取键名
- for(let key of m.keys()){
- console.log(key);
- }
- //打印结果:name
- // age
- //使用values方法获取键值
- for(let value of m.values()){
- console.log(value);
- }
- //打印结果:前端君
- // 25
keys方法和values方法的使用方式一致,只是返回的结果不同。
forEach( )方法
除了使用以上三个方法实现遍历以外,我们还可以使用forEach遍历每一个键值对:
- let m = new Map([
- ["name","前端君"],
- ["age",25]
- ]);
- m.forEach(function(value,key){
- console.log(key+':'+value);
- });
- //打印结果:name:前端君
- // age:25
forEach方法接收一个匿名函数,给匿名函数传参value和key,分别是Map实例的键名和键值,这个方法的使用相信大家一定不会陌生。
size属性
其中一个常用的属性就是size:获取实例的成员数。
- let m = new Map();
- m.set(1,3);
- m.set('1','3');
- m.size;//结果:2
使用set方法给实例m添加了两个键值对成员,所以实例的 size为:2。
什么是WeakMap
讲了Map结构,我们现在讲WeakMap结构。
WeakMap结构和Map结构很类似,不同点在于**WeakMap结构的键名只支持引用类型的数据。**哪些是引用类型的值呢?比如:数组,对象,函数。
关于什么是引用类型,其中涉及到了传址和传值的区别,还记得装修工张师傅和王师傅的例子吗?第三节有详细的讲解,点击可查看。
WeakMap的基本用法
WeakMap结构的使用方式和Map结构一样:
- let wm = new WeakMap();
两者都是使用new来创建实例。如果添加键值对的话,我们同样是使用set方法,不过键名的类型必须要求是引用类型的值,我们来看看:
- let wm = new WeakMap();
- //数组类型的键名
- wm.set([1],2);
- //对象类型的键名
- wm.set({'name':'Zhangsan'},2);
- //函数类型的键名
- function fn(){};
- wm.set(fn,2);
- console.log(wm);
- //打印:WeakMap {
- [1] => 2,
- Object {name: "Zhangsan"} => 2,
- function => 2
- }
从打印结果可以看出,以上类型的键名都可以成功添加到WeakMap实例中。
WeakMap和Map的区别
如果是普通的值类型则不允许。比如:字符串,数字,null,undefined,布尔类型。而Map结构是允许的,这就是两者的不同之处,谨记。
跟Map一样,WeakMap也拥有get、has、delete方法,用法和用途都一样。不同地方在于,WeakMap不支持clear方法,不支持遍历,也就没有了keys、values、entries、forEach这4个方法,也没有属性size。
理由跟WeakSet结构一样:键名中的引用类型是弱引用,你永远不知道这个引用对象什么时候会被垃圾回收机制回收了,如果这个引用类型的值被垃圾机制回收了,WeakMap实例中的对应键值对也会消失。
本节小结
总结:Map结构是一个键值对的集合,跟Object对象不同的是,Map结构的键名可以是任何类型的值,而WeakMap结构的键名只允许是引用类型的值。
它们都提供了各自的方法和属性供开发者使用:set、get、has、delete等相同的方法,其中Map结构还多了clear方法,size属性和一些用于遍历的方法:keys、values、entries、forEach。
更多前端学习内容文章干货请关注我的专栏(不断更新)
阿里名厂标准web前端高级工程师教程目录大全,从基础到进阶,看完保证您的薪资上升一个台阶
在这里我给大家准备了很多的学习资料
其实你与阿里工程师的差距只差这些东西
ES6新增的Map和WeakMap 又是什么玩意?非常详细的解释的更多相关文章
- ES6新增的 Set 和 WeakSet 是什么玩意?在此揭晓
现在的章节内容会更加的紧密,如果大家看不懂可以先去看以前的文章,当然看了的忘了,也可以去看一下,这样学习后面的内容才会更加容易. 什么是Set结构 Set是ES6给开发者带来的一种新的数据结构,你可以 ...
- ES6新增的数据类型Map和Set。
Javascript的默认对象表示方式 {} ,即一组键值对. 但是Javascript的对象有个小问题,就是键必须是字符串.但实际上Number或者其他数据类型作为键也是非常合理的. 为了解决这个问 ...
- ES6 中的 Set、Map 和 WeakMap
Set 是 ES6 新增的有序列表集合,它不会包含重复项. Set 支持 add(item) 方法,用来向 Set 添加任意类型的元素,如果已经添加过则自动忽略: has(item) 方法用来检测 S ...
- ES6新增的常用数组方法(forEach,map,filter,every,some)
ES6新增的常用数组方法 let arr = [1, 2, 3, 2, 1]; 一 forEach => 遍历数组 arr.forEach((v, i) => { console.log( ...
- ES6 Set,WeakSet,Map,WeakMap
1. Set Set是一个集合,里面的值都是唯一的,没有重复的.Set中可以是任何数据类型,并且添加数据时会进行严格比较,重复数据无法加入. 2. WeakSet 弱引用Set.只能存储对象,不能存储 ...
- es6入门7--Set Map数据结构
本文作为ES6入门第十三章的学习整理笔记,可能会包含少部分个人的理解推测,若想阅读更详细的介绍,还请阅读原文ES6入门 一.set数据结构 1.set不接受重复值 ES6新增了Set构造函数用于创建s ...
- js ES6 Set和Map数据结构详解
这篇文章主要介绍了ES6学习笔记之Set和Map数据结构,结合实例形式详细分析了ECMAScript中基本数据结构Set和Map的常用属性与方法的功能.用法及相关注意事项,需要的朋友可以参考下 本 ...
- Map 和 WeakMap 数据结构
Map 和 WeakMap 是ES6 新增的数据结构 一.Map 它们本质与对象一样,都是键值对的集合,但是他们与 Object 对象主要的不同是,键可以是各种类型的数值,而Object 对象的键 只 ...
- ES6 Set 和 Map
ES5 模拟Set 与 Map 集合 Set 常用于检查对象中是否存在某个键名 Map集合常被用于获取已存的信息 所有对象的属性名必须是字符串,那么必须确保每个键名都是字符串类型且在对象中是唯一的 数 ...
随机推荐
- Redis 主从复制机制(集群)与 哨兵机制
1,什么是redis 主从复制 支持多个数据库之间的数据同步.只能一个主数据库(master),可以一个或者多个从数据库(slave) 主数据库,可以读写 从数据库,只可以读 当主数据库,做写的操作的 ...
- HFSS——平面正弦加载阿基米德螺旋线模型设计
这学期开始进入HFSS的学习,这是软件应该是电磁相关专业必须掌握的软件之一.前几天图老师发布第一个模型设计任务,是关于平面正弦加载阿基米德螺旋线,拿到具体要求后,就去网上找资料,发现有关HFSS的资料 ...
- [vijos1554&bzoj1411]硬币游戏<快速幂>
题目链接:https://vijos.org/p/1554 http://www.lydsy.com/JudgeOnline/problem.php?id=1411 这题真的淫*QAQ... 一看题还 ...
- Python常用模块之configparser
ConfigParser简介 ConfigParser 是用来读取配置文件的包.配置文件的格式如下:中括号“[ ]”内包含的为section.section 下面为类似于key-value 的配置内容 ...
- B【USACO 2015 Jan Gold】牧草鉴赏家
时间限制 : 10000 MS 空间限制 : 65536 KB 问题描述 约翰有n块草场,编号1到n,这些草场由若干条单行道相连.奶牛贝西是美味牧草的鉴赏家,她想到达尽可能多的草场去品尝牧草. 贝 ...
- 为何关键字static在面试中频频被问?
关键字static的神奇妙用在今天的学习中,我了解到关键字static的作用,下面我来给大家分享一下.①static 修饰局部变量只改变了变量的生命周期,让静态局部变量出了作用域依然存在,到程序结束生 ...
- RedHat 6.7 使用 CentOS 6 的源
1. 移除 RedHat 相关软件包 # yum -y remove subscription-manager and rh-check # rpm -aq | grep yum | xargs rp ...
- STM32F103ZET6串口通信
1.电平标准 根据通讯使用的电平标准不同,串口通讯可分为TTL标准和RS-232标准,如下表: 从图中可以看到,TTL电平标准使用5V表示高电平,使用0V表示低电平.在R232电平标准中,为了增加串口 ...
- 无法加载文件 C:\Users\Administrator\AppData\Roaming\npm\vue.ps1,因为在此系统··········
网上百度了下,解决方案是: 1. 以管理员身份运行PowerShell2. 执行:get-ExecutionPolicy,回复Restricted,表示状态是禁止的3.执行:set-Execution ...
- JS中this指向问题和改变this指向
首先必须要说的是,this的指向在函数定义的时候是确定不了的,只有函数执行的时候才能确定this到底指向谁,实际上this的最终指向的是那个调用它的对象(这句话有些问题,后面会解释为什么会有问题,虽然 ...