iis服务器助手广告
返回顶部
首页 > 资讯 > 前端开发 > JavaScript >JavaScript WeakMap的具体使用
  • 273
分享到

JavaScript WeakMap的具体使用

JavaScript WeakMap 2023-02-17 12:02:14 273人浏览 独家记忆
摘要

目录前言一、为何选用WeakMap1. Map2. WeakMap二、WeakMap原型方法总结前言 我在处理一个复杂对象的深拷贝方法时接触到WeakMap, 其作为缓存结构以解决对

前言

我在处理一个复杂对象的深拷贝方法时接触到WeakMap, 其作为缓存结构以解决对象内部的循环引用问题. 为了改造这个方法, 决定研究WeakMap.

一、为何选用WeakMap

WeakMap和Map都可以使用对象作为键, Map也可以使用基本数据类型作为键, 在特殊的情况下(都使用对象作为键), 两者看起来并无差别.

1. Map

Map会阻止javascript的内存回收机制对 以一个已经被回收的对象作为键的元素 进行回收.
与Map内存储元素的方式有关:

A map api could be implemented in JavaScript with two arrays (one for keys, one for values) shared by the four API methods.
`map`在JavaScript内可通过使两个数组被4种方法共享来实现, 向`Map`内设置元素时分别将键和值`push`进这两个数组.
Setting elements on this map would involve pushing a key and value onto the end of each of those arrays simultaneously.
访问`Map`取值时需要遍历, 从两个数组内找到匹配的值.

var sayings = new Map();
sayings.set('dog', 'woof');
sayings.set('cat', 'meow');
sayings.set('elephant', 'toot');
sayings.size; // 3
sayings.get('fox'); // undefined
sayings.has('bird'); // false
sayings.delete('dog');
sayings.has('dog'); // false

for (var [key, value] of sayings) {
  console.log(key + ' Goes ' + value);
}
// "cat goes meow"
// "elephant goes toot"

sayings.clear();
sayings.size; // 0

首先Map内部基于数组实现, 取值赋值需要遍历, 时间复杂度上来了:

The first one is an O(n) set and search (n being the number of keys in the map)
首先设置和查找的时间复杂度都是O(n), n是Map内键的数量.
since both operations must iterate through the list of keys to find a matching value.
因为两个操作都必须遍历每一个键以找到匹配的值.

其次数组会一直保留着对元素的引用, 这跟元素是否为引用类型无关, 只要数组不被销毁, 元素的引用也不会被销毁:

let ele1 = 'ele1';
let ele2 = { key: 'value' };

let arr = [ ele1, ele2 ];

ele1 = null; // 设置为null脱离当前执行环境, 以便回收机制回收
ele2.key = null;

console.log(arr);
// [ 'ele1', { key: 'null' } ]

前面提到Map内部可以通过两个数组实现, 那么意味着在Map需要销毁前, Map内的键和值都无法被JavaScript垃圾回收机制回收, Map可能会变得臃肿庞大导致内存不足(内存泄漏).

持有原始对象引用的映射实际上意味着对象不能被垃圾回收, 这可能会导致意外的内存问题.
如果你希望存储在映射中的对象具有与原始对象相同的生命周期, 请考虑使用 WeakMap.

2. WeakMap

WeakMap同Map是键值对的集合, 但它的键被弱保持, 即当键所指的对象未在其他地方被引用时, 将被垃圾回收机制回收.
其键必须是对象, 值可以是任意数据类型.

也由于这种弱引用实现的垃圾回收可执行, WeakMap内元素的存在变得不可预知(可能垃圾回收机制目前没有回收至此处, 但此处应当回收.), 为了防止执行时出现意外, WeakMap没有提供枚举方法.

正由于这样的弱引用, WeakMap的key是不可枚举的(没有方法能给出所有的 key).
如果key可枚举, 其列表将受垃圾回收机制的影响, 从而得到不确定的结果。

但是WeakMap提供的接口与Map相同, 可以通过接口稳定的访问元素.

let ele1 = { key: "value" };

let weak = new WeakMap();
weak.set(ele1, "ele1");

ele1 = null;

console.log(weak); // WeakMap { <items unknown> } 不赋值null此处结果相同
console.log(weak.get(ele1)); // undefined 销毁 不赋值null此处为'ele1'

总之, 相比Map, 它更干净利落, 更节约内存.
但是你如果有枚举需求, 或者就是需要一直保存着key不回收, 那就用Map.

二、WeakMap原型方法

指明需要何种操作, 并指明需要操作的键值对的key, 直接传变量即可.

方法描述
WeakMap.prototype.delete(key)删除WeakMap中与key相匹配的value.
WeakMap.prototype.get(key)返回WeakMap中与key相关联的值, 如果key不存在则返回undefined.
WeakMap.prototype.has(key)返回布尔值, 断言WeakMap对象中该key是否存在.
WeakMap.prototype.set(key, value)WeakMap中设置一组新的键值对, 返回设置完毕后的WeakMap对象.

总结

到此这篇关于JavaScript WeakMap的具体使用的文章就介绍到这了,更多相关JavaScript WeakMap内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: JavaScript WeakMap的具体使用

本文链接: https://www.lsjlt.com/news/196535.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • JavaScript WeakMap的具体使用
    目录前言一、为何选用WeakMap1. Map2. WeakMap二、WeakMap原型方法总结前言 我在处理一个复杂对象的深拷贝方法时接触到WeakMap, 其作为缓存结构以解决对...
    99+
    2023-02-17
    JavaScript WeakMap
  • JavaScript中的new操作符的具体使用
    JavaScript中的new操作符是一个非常重要的概念,它可以让我们创建一个自定义的对象类型或者一个内置的对象类型,比如Array、Date、Function等。那么,new操作符...
    99+
    2023-05-18
    JavaScript new操作符 js new运算符
  • JavaScript中setTimeout()的具体用法
    setTimeout( ) 是属于 window 的 方法, 但我们都是略去 window 这顶层容器名称, 这是用来设定一个时间, 时间到了, 就会执行一个指定的 method 请...
    99+
    2023-05-17
    JavaScript setTimeout()
  • Quartz.NET的具体使用
    目录一、什么是Quartz.NET?二、Quartz.NET可以做什么?三、ASP.NET Core如何使用Quartz.NET?四、Quartz的cron表达式一、什么是Quart...
    99+
    2024-04-02
  • JavaScheduledExecutorService的具体使用
    目录1. 延迟不循环任务schedule方法2. 延迟且循环cheduleAtFixedRate方法3. 严格按照一定时间间隔执行``ScheduledExecutorService...
    99+
    2023-05-19
    ScheduledExecutorService
  • QtQFrame的具体使用
    目录1.概述2.常用数据接口3.示例1.概述 void setFrameShape(Shape) QFrame继承QWidget,QFrame类是具有框架的小部件的基类,例如QLab...
    99+
    2024-04-02
  • python__add__()的具体使用
    __add__(),  同一个类,两个对象相加的实现逻辑,重写 + class Myclass(object): def __init__(self,value):...
    99+
    2023-02-27
    python __add__()使用 python __add__
  • pythonhttpx的具体使用
    目录什么是 Httpx安装 Httpx发送 HTTP 请求发送异步 HTTP 请求设置请求标头设置请求参数发送请求体发送 JSON 数据设置超时错误处理证书验证使用代理上传文件使用 ...
    99+
    2023-05-14
    python httpx
  • np.unique()的具体使用
    目录一、np.unique() 介绍二、np.unique() 原型三、实例参考链接一、np.unique() 介绍 对于一维数组或者列表,np.unique() 函数 去除其中重复...
    99+
    2023-03-14
    np.unique()使用 np.unique()
  • 深入探究JavaScript中WeakMap的原理与用法
    目录WeakMap的原理WeakMap的用法对象私有属性缓存计算结果隐藏对象属性注意事项总结在JavaScript中,对象是一种非常重要的数据类型。我们可以使用对象来保存和管理数据,...
    99+
    2023-05-20
    JavaScript WeakMap原理 JavaScript WeakMap用法 JavaScript WeakMap
  • python-httpx的具体使用
    目录安装创建请求自定义头部超时时间SSL证书认证请求类型Query ParamsForm表单文件上传JSON二进制数据响应响应类型Cookie重定向历史httpx.Client合并/...
    99+
    2024-04-02
  • Vuex localStorage的具体使用
    目录状态管理的必要性localStorage储存和获取数据生命周期VuexVuex的概念Vuex的工作流程Vuex和localStorage的区别总结前端开发中,状态管理是一个很重要...
    99+
    2023-05-20
    Vuex localStorage
  • numpy.reshape(-1,1)的具体使用
    数组新的shape属性应该要与原来的配套,如果等于-1的话,那么Numpy会根据剩下的维度计算出数组的另外一个shape属性值。 举个例子: x = np.array([[2, 0]...
    99+
    2024-04-02
  • GO的range具体使用
    目录GO 语言的 for…range  能做什么呢?for…range  如何使用 ?数组 array切片 slicechannel 通道for…rang...
    99+
    2024-04-02
  • C# Volatile的具体使用
    目录​1.Overview2.Detail3.Conclusion4.Reference​1.Overview 经常研究.NET源码库的小伙伴会经常看到一个关...
    99+
    2024-04-02
  • podman容器工具的具体使用
    目录podman简介Podman和Docker的主要区别是什么?podman安装使用配置镜像加速相关工具podman简介 Podman是一个开源项目,可在大多数Linux平台上使用并...
    99+
    2024-04-02
  • numpy.insert()的具体使用方法
    目录1. 参数说明2. 示例2.1. 插入一列,值为标量2.2. 插入一列,值为一维矩阵2.3. 插入多列,值为标量2.4. 输入为一维向量2.5. 输入为矩阵numpy.inser...
    99+
    2023-02-09
    numpy.insert()使用
  • Pytest断言的具体使用
    目录assert断言方法异常断言Excepiton检查断言装饰器Pytest使用的断言是使用python内置的断言assert。Python assert(断言)用于判断一个表达式,...
    99+
    2023-02-07
    Pytest断言
  • React中useRef的具体使用
    相信有过React使用经验的人对ref都会熟悉,它可以用来获取组件实例对象或者是DOM对象。 而useRef这个hooks函数,除了传统的用法之外,它还可以“跨渲染周期”保存数据。 ...
    99+
    2024-04-02
  • nginx之queue的具体使用
    目录一、简介二、数据结构三、相关API3.1 初始化一个队列3.2 判断队列是否为空3.3 队头插入节点3.4 队尾插入节点3.5 从队列中移除某个节点3.6 将队列从某个节点拆分成...
    99+
    2024-04-02
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作