IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> JavaScript知识库 -> 【JS】垃圾回收机制 -> 正文阅读

[JavaScript知识库]【JS】垃圾回收机制

垃圾回收机制

  1. 垃圾回收GC的全拼是 Garbage Collection
  2. 其在维基百科的定义是: 在计算机科学中,垃圾回收(英语:Garbage Collection,缩写为GC)是一种自动的内存管理机制。
  3. 当一个电脑上的动态内存不再需要时,就应该予以释放,以让出内存,这种内存资源管理,称为垃圾回收(garbage collection)
  • 有些语言(比如 C 语言)必须手动释放内存,程序员负责内存管理。
//  C 语言代码
char * buffer;
buffer = (char*) malloc(42);	// malloc方法用来申请内存

// Do something with buffer
free(buffer);	// 使用完毕之后,必须自己用free方法释放内存。
  • 这很麻烦,所以大多数语言提供自动内存管理,减轻程序员的负担,这被称为"垃圾回收机制"(garbage collector)
  • 垃圾回收机制怎么知道,哪些内存不再需要呢?这就要牵涉到一些垃圾回收算法了
  • 常见的垃圾回收算法:
1. 引用计数算法
2. 标记清除算法
3. 标记压缩算法
4. 待续。。。。
  • 垃圾回收算法性能体现:
1. 吞吐量 throughput
2. 最大暂停时间
3. 堆使用效率
4. 访问的局部性

引用计数算法

  • 这是最初级的垃圾收集算法。
  • 此算法把“对象是否不再需要”简化定义为“对象有没有其他对象引用到它”。
  • 如果没有引用指向该对象(零引用),对象将被垃圾回收机制回收。
  • 该算法有个限制:无法处理循环引用的事例。

  • 示例:如果一个值不再需要了,引用数却不为0,垃圾回收机制无法释放这块内存,从而导致内存泄漏。
let arr = [1, 2, 3, 4];
console.log('hello world');
数组[1, 2, 3, 4]是一个值,会占用内存。
变量arr是仅有的对这个值的引用,因此引用次数为1。
尽管后面的代码没有用到arr,它还是会持续占用内存。
  • 如果增加一行代码,解除arr对[1, 2, 3, 4]引用,这块内存就可以被垃圾回收机制释放了。
let arr = [1, 2, 3, 4];
console.log('hello world');
arr = null;
// arr重置为null,就解除了对[1, 2, 3, 4]的引用
// 引用次数变成了0,内存就可以释放出来了

  • 示例:
var o = {
  a: {
    b:2
  }
};
// 两个对象被创建,一个作为另一个的属性被引用,另一个被分配给变量o
// 很显然,没有一个可以被垃圾收集


var o2 = o; // o2变量是第二个对“这个对象”的引用

o = 1;      // 现在,“这个对象”只有一个o2变量的引用了,“这个对象”的原始引用o已经没有

var oa = o2.a; // 引用“这个对象”的a属性
               // 现在,“这个对象”有两个引用了,一个是o2,一个是oa

o2 = "yo"; // 虽然最初的对象现在已经是零引用了,可以被垃圾回收了
           // 但是它的属性a的对象还在被oa引用,所以还不能回收

oa = null; // a属性的那个对象现在也是零引用了
           // 它可以被垃圾回收了
  • 示例:循环引用限制
function f(){
  var o = {};
  var o2 = {};
  o.a = o2; // o 引用 o2
  o2.a = o; // o2 引用 o

  return "azerty";
}

f();
例子中,两个对象被创建,并互相引用,形成了一个循环。
它们被调用之后会离开函数作用域,所以它们已经没有用了,可以被回收了。
然而,引用计数算法考虑到它们互相都有至少一次引用,所以它们不会被回收。

标记清除算法

  1. 从2012年起,所有现代浏览器都使用了标记清除垃圾回收算法。
  2. 所有对 JavaScript 垃圾回收算法的改进都是基于标记清除算法的改进。
  3. 并没有改进标记清除算法本身和它对“对象是否不再需要”的简化定义。
  • 这个算法把“对象是否不再需要”简化定义为“对象是否可以获得”。
1. 这个算法假定设置一个叫做根(root)的对象(在Javascript里,根是全局对象)。
2. 垃圾回收器将定期从根开始,找所有从根开始引用的对象,然后找这些对象引用的对象……从根开始,
3. 垃圾回收器将找到所有可以获得的对象和收集所有不能获得的对象。
4. 这个算法比引用计数算法要好,因为“有零引用的对象”总是不可获得的,但是相反却不一定
  • 例如,对象结构如下:

在这里插入图片描述

  • 我们可以清楚地看到右边有一个“不可到达的块”。
  • 现在让我们看看“标记并清除”垃圾回收器如何处理它。
  1. 垃圾回收器获取根并“标记”(记住)它们

在这里插入图片描述

  1. 然后标记他们的引用

在这里插入图片描述

  1. 以及子孙代的引用:

在这里插入图片描述

  1. 现在进程中不能访问的对象被认为是不可访问的,将被删除:

在这里插入图片描述


  • 示例:循环引用不再是问题了
  • 函数调用返回之后,两个对象从全局对象出发无法获取。
  • 因此,他们将会被垃圾回收器回收
function f(){
  var o = {};
  var o2 = {};
  o.a = o2; // o 引用 o2
  o2.a = o; // o2 引用 o

  return "azerty";
}

f();

  • 限制:那些无法从根对象查询到的对象都将被清除

尽管这是一个限制,但实践中我们很少会碰到类似的情况,所以开发者不太会去关心垃圾回收机制。


常见的改进和优化

  • 分代回收
1. 对象分为两组:“新对象”和“旧对象”。
2. 许多对象出现,完成它们的工作并迅速结 ,它们很快就会被清理干净。
3. 那些活得足够久的对象,会变“老”,并且很少接受检查。
  • 增量回收
1. 如果有很多对象,并且我们试图一次遍历并标记整个对象集,那么可能会花费一些时间,并在执行中会有一定的延迟。
2. 因此,引擎试图将垃圾回收分解为多个部分,然后,各个部分分别执行。
3. 这需要额外的标记来跟踪变化,这样有很多微小的延迟,而不是很大的延迟。
  • 空闲时间收集
1. 垃圾回收器只在 CPU 空闲时运行,以减少对执行的可能影响。
  JavaScript知识库 最新文章
ES6的相关知识点
react 函数式组件 & react其他一些总结
Vue基础超详细
前端JS也可以连点成线(Vue中运用 AntVG6)
Vue事件处理的基本使用
Vue后台项目的记录 (一)
前后端分离vue跨域,devServer配置proxy代理
TypeScript
初识vuex
vue项目安装包指令收集
上一篇文章      下一篇文章      查看所有文章
加:2021-12-08 13:43:31  更:2021-12-08 13:43:46 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 7:43:00-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码