自动化的内存管理技术之垃圾回收机制-JavaScript引用数据内存回收机制

垃圾回收机制(Garbage Collection, GC) 是一种自动化的内存管理技术,用于回收程序中不再使用的内存空间,避免内存泄漏。JavaScript(尤其是 V8 引擎)使用了一些经典的垃圾回收算法,如 标记-清除分代回收

以下是垃圾回收的原理和具体机制的详细解析:


1. 垃圾回收的核心目标

垃圾回收的主要任务是:

  1. 找出不再被引用的对象(不可达的对象)。
  2. 释放这些对象所占用的内存空间。
  3. 确保程序有充足的内存可以继续运行。

2. 常见垃圾回收算法

(1) 标记-清除算法(Mark-and-Sweep)

这是最基础、最常用的垃圾回收算法。

工作原理
  1. 标记阶段(Marking Phase)

    • 从根对象(如全局对象、栈中的局部变量)出发,递归检查每个对象是否可以到达。
    • 所有可达的对象都会被标记为“活跃”状态。
  2. 清除阶段(Sweeping Phase)

    • 遍历整个内存区域,回收没有被标记的“不可达”对象,并释放它们占用的内存。
示意图
初始内存状态:
[根对象] --> [对象A] --> [对象B][对象C](无引用)标记阶段:
根对象、对象A、对象B 被标记为“活跃”。
对象C 被标记为“不可达”。清除阶段:
回收对象C。
优点
  • 简单高效,适合大多数情况。
缺点
  • 垃圾回收期间可能暂停程序执行(称为“停顿”),影响性能。

(2) 分代回收算法(Generational GC)

现代 JavaScript 引擎(如 V8)引入了分代垃圾回收机制,将内存划分为两代:

  • 新生代:存放短期存活的对象(如局部变量、临时对象)。
  • 老生代:存放长期存活的对象(如全局对象、大型缓存)。
工作原理
  1. 新生代和老生代分别使用不同的垃圾回收策略:

    • 新生代垃圾回收:采用Scavenge算法,因为新生代中的大多数对象存活时间短,清理时只关注少量存活对象。
    • 老生代垃圾回收:采用标记-清除标记-整理算法,因为老生代中对象存活时间较长,内存碎片化问题更严重。
  2. 当新生代的对象存活时间足够长时,会被移动到老生代(称为晋升)。

Scavenge算法(用于新生代)
  • 将新生代内存分为两个区域:From 空间To 空间
  • 活跃对象从 From 空间复制到 To 空间。
  • 清空 From 空间,交换 From 和 To 空间角色。

(3) 引用计数算法(Reference Counting)

这是另一种垃圾回收方法,通过跟踪对象的引用次数来判断对象是否可以被回收。

工作原理
  • 每个对象维护一个“引用计数”。
  • 当有新的引用指向对象时,计数 +1。
  • 当引用被移除时,计数 -1。
  • 如果计数为 0,回收该对象。
缺点
  • 无法处理循环引用
    let a = {};
    let b = {};
    a.ref = b;
    b.ref = a;
    // 两者引用计数都不为 0,但实际上已无法访问。
    

由于这个问题,JavaScript 已很少使用引用计数,而采用更强大的标记-清除算法。


3. 垃圾回收的优化机制

(1) 增量回收(Incremental GC)

为了减少标记-清除算法中的全局暂停,增量回收将垃圾回收的过程拆分为多个小步骤,逐步完成垃圾回收。

(2) 并发回收(Concurrent GC)

垃圾回收操作与主线程的代码执行并发进行,进一步减少停顿时间。

(3) 增量标记(Incremental Marking)

在标记阶段分多次完成扫描,避免一次性暂停程序执行。


4. JavaScript 垃圾回收中的 V8 引擎实现

V8 引擎采用了分代垃圾回收机制,结合了标记-清除和增量回收策略:

  1. 新生代垃圾回收(Scavenge)

    • 小对象存活时间短,快速回收。
    • 复制存活对象,清空其余内存。
  2. 老生代垃圾回收(Mark-and-Sweep / Mark-and-Compact)

    • 使用标记-清除算法,定期整理内存以减少碎片。

5. 代码实践中的影响

避免内存泄漏的常见情况
  • 未清理的全局变量
    window.globalVar = "I'm here forever";
    
  • 闭包引用
    function outer() {let obj = { key: "value" };return function inner() {console.log(obj);};
    }
    let closure = outer();
    // obj 将一直被引用,不会被回收。
    
  • 事件监听未移除
    const element = document.getElementById("button");
    element.addEventListener("click", () => {console.log("Clicked");
    });
    // 如果 element 被移除但事件监听器未清理,内存无法释放。
    
优化内存使用的建议
  1. 尽量避免创建不必要的全局变量。
  2. 使用 WeakMapWeakSet 存储可能被销毁的对象引用。
  3. 确保手动移除事件监听器和 DOM 节点引用。

总结来说,垃圾回收机制极大简化了 JavaScript 的内存管理,但了解其原理和局限性有助于编写更高效和稳定的代码。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/479018.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

全网最早Towards Generalizable Multi-Object Tracking—通用跟踪器的点跟踪CVPR2024

Towards Generalizable Multi-Object Tracking—迈向可推广的多目标跟踪 原标题:Towards Generalizable Multi-Object Tracking 论文链接:https://arxiv.org/pdf/2406.00429 代码链接:https://github.com/qinzheng2000/GeneralTrack.git 作者…

MyBatis框架-动态SQL-XML中的常用标签+特殊字符在XML中的显示

一、if标签、where标签、trim标签、choose标签、set标签、foreach标签 1、问题引入:where关键字和and关键字在动态SQL里面应该如何添加? (1)if标签: test属性的值是判断条件 if标签里面的内容是条件成立时添加到SQ…

探秘嵌入式位运算:基础与高级技巧

目录 一、位运算基础知识 1.1. 位运算符 1.1.1. 与运算(&) 1.1.2. 或运算(|) 1.1.3. 异或运算(^) 1.1.4. 取反运算(~) 1.1.5. 双重按位取反运算符(~~&#xf…

渗透测试笔记—shodan(7完结)

声明: 学习视频来自B站up主 【泷羽sec】有兴趣的师傅可以关注一下,如涉及侵权马上删除文章,笔记只是方便各位师傅的学习和探讨,文章所提到的网站以及内容,只做学习交流,其他均与本人以及泷羽sec团队无关&am…

2024年最新版Java八股文复习

最新版本Java八股文复习,每天更新一篇,博主正在持续努力更新中~~~ 一、Java基础篇1、怎么理解面向对象?简单说说封装、继承、多态三大特性?2、多态体现在哪几个方面?3、面向对象的设计原则你知道有哪些吗?4…

Notepad++ 替换所有数字给数字加单引号

前言 今天遇到这样一个场景: 要去更新某张表里 code1,2,3,4,5,6 的数据,把它的 name 设置为 ‘张三’ 但是 code在数据库里面的字段类型是 vachar(64),它自身携带索引 原本可以这样写 SQL: update tableA set namezhangsan where code in …

前端图像处理(一)

目录 一、上传 1.1、图片转base64 二、图片样式 2.1、图片边框【border-image】 三、Canvas 3.1、把canvas图片上传到服务器 3.2、在canvas中绘制和拖动矩形 3.3、图片(同色区域)点击变色 一、上传 1.1、图片转base64 传统上传: 客户端选择图片&#xf…

推荐一款龙迅HDMI2.0转LVDS芯片 LT6211UX LT6211UXC

龙迅的HDMI2.0转LVDS芯片LT6211UX和LT6211UXC是两款高性能的转换器芯片,它们在功能和应用上有所差异,同时也存在一些共同点。以下是对这两款芯片的详细比较和分析: 一、LT6211UX 主要特性: HDMI2.0至LVDS和MIPI转换器。HDMI2.0输…

51单片机从入门到精通:理论与实践指南入门篇(二)

续51单片机从入门到精通:理论与实践指南(一)https://blog.csdn.net/speaking_me/article/details/144067372 第一篇总体给大家在(全局)总体上讲解了一下51单片机,那么接下来几天结束详细讲解,从…

STM32C011开发(3)----Flash操作

STM32C011开发----3.Flash操作 概述硬件准备视频教学样品申请源码下载参考程序生成STM32CUBEMX串口配置堆栈设置串口重定向FLASH数据初始化FLASH 读写演示 概述 STM32C011 系列微控制器内置 Flash 存储器,支持程序存储与数据保存,具备页面擦除、双字写入…

IDEA无法创建java8、11项目创建出的pom.xml为空

主要是由于Spring3.X版本不支持JDK8,JDK11,最低支持JDK17 解决的话要不就换成JDK17以上的版本,但是不太现实 另外可以参考以下方式解决 修改spring初始化服务器地址为阿里云的 https://start.aliyun.com/

【Unity3D】创建自定义字体

前置准备 如图所示,项目工程中需要用文件夹存储0-9的Sprite图片。 使用流程 直接右键存放图片的文件夹,选择【创建自定义字体】,之后会在脚本定义的FontOutputPath中生成材质球和字体。 源码 using System; using System.Collections.Gene…

logminer挖掘日志归档查找问题

--根据发生问题时间点查找归档文件 select first_time,NAME from gv$archived_log where first_time>2016-03-15 17:00:00 and first_time<2016-03-15 21:00:00; 2016-03-15 17:23:55 ARCH/jxdb/archivelog/2016_03_15/thread_1_seq_41588.4060.906577337 2016-03-15 17:…

电商项目高级篇06-缓存

电商项目高级篇06-缓存 1、docker下启动redis2、项目整合redis 缓存 流程图&#xff1a; data cache.load(id);//从缓存加载数据 If(data null){ data db.load(id);//从数据库加载数据 cache.put(id,data);//保存到 cache 中 } return data;在我们的单体项目中可以用Map作…

如何使用GCC手动编译stm32程序

如何不使用任何IDE&#xff08;集成开发环境&#xff09;编译stm32程序? 集成开发环境将编辑器、编译器、链接器、调试器等开发工具集成在一个统一的软件中&#xff0c;使得开发人员可以更加简单、高效地完成软件开发过程。如果我们不使用KEIL,IAR等集成开发环境&#xff0c;…

一个专为云原生环境设计的高性能分布式文件系统

大家好&#xff0c;今天给大家分享一款开源创新的分布式 POSIX 文件系统JuiceFS&#xff0c;旨在解决海量云存储与各类应用平台&#xff08;如大数据、机器学习、人工智能等&#xff09;之间高效对接的问题。 项目介绍 JuiceFS 是一款面向云原生设计的高性能分布式文件系统&am…

Vue-TreeSelect组件最下级隐藏No sub-options

问题&#xff1a;最下级没有数据的话&#xff0c;去除No sub-options信息 为什么没下级&#xff0c;会展示这个&#xff1f; 整个树形结构数据都是由后端构造好返回给前端的。默认子类没数据的话&#xff0c;children是一个空数组。也就是因为这最下级的空数组&#xff0c;导致…

k8s集群增加nfs-subdir-external-provisioner存储类

文章目录 前言一、版本信息二、本机安装nfs组件包三、下载nfs-subdir-external-provisioner配置文件并进行配置1.下载文件2.修改配置 三、进行部署备注&#xff1a;关于镜像无法拉取问题的处理 前言 手里的一台服务器搭建一个单点的k8s集群&#xff0c;然后在本机上使用nfs-su…

C语言数据结构-链表

C语言数据结构-链表 1.单链表1.1概念与结构1.2结点3.2 链表性质1.3链表的打印1.4实现单链表1.4.1 插入1.4.2删除1.4.3查找1.4.4在指定位置之前插入或删除1.4.5在指定位置之后插入或删除1.4.6删除指定位置1.4.7销毁链表 2.链表的分类3.双向链表3.1实现双向链表3.1.1尾插3.1.2头插…

【SpringCloud详细教程】-04-服务容错--Sentinel

精品专题&#xff1a; 01.《C语言从不挂科到高绩点》课程详细笔记 https://blog.csdn.net/yueyehuguang/category_12753294.html?spm1001.2014.3001.5482 02. 《SpringBoot详细教程》课程详细笔记 https://blog.csdn.net/yueyehuguang/category_12789841.html?spm1001.20…