首页 > 其他分享 >浅谈浏览器垃圾回收机制

浅谈浏览器垃圾回收机制

时间:2022-08-19 22:34:44浏览次数:105  
标签:垃圾 obj 浅谈 回收 引用 var 浏览器 变量

浅谈浏览器垃圾回收机制

GoldenSide 0.2952019.02.18 17:23:20字数 1,158阅读 6,844
一、垃圾回收机制原理

   由于字符串、对象和数组没有固定大小,所有当他们的大小已知时,才能对他们进行动态的存储分配。JavaScript程序每次创建字符串、数组或对象时,解释器都必须分配内存来存储那个实体。只要像这样动态地分配了内存,最终都要释放这些内存以便他们能够被再用,否则,JavaScript的解释器将会消耗完系统中所有可用的内存,造成系统崩溃。

二、垃圾回收原理浅析

  现在各大浏览器通常用采用的垃圾回收有两种方法:标记清除、引用计数。
1、标记清除(mark and sweep)
  大部分浏览器以此方式进行垃圾回收,当变量进入执行环境(函数中声明变量,执行时)的时候,垃圾回收器将其标记为“进入环境”,当变量离开环境的时候(函数执行结束)将其标记为“离开环境”,在离开环境之后还有的变量则是需要被删除的变量。标记方式不定,可以是某个特殊位的反转或维护一个列表等。
  垃圾收集器给内存中的所有变量都加上标记,然后去掉环境中的变量以及被环境中的变量引用的变量的标记。在此之后再被加上的标记的变量即为需要回收的变量,因为环境中的变量已经无法访问到这些变量。

关于这一块,建议读读Tom大叔的几篇文章,关于作用域链的一些知识详解,读完差不多就知道了,哪些变量会被做标记。

2、引用计数

  另一种不太常见的垃圾回收策略是引用计数。引用计数的含义是跟踪记录每个值被引用的次数。当声明了一个变量并将一个引用类型赋值给该变量时,则这个值的引用次数就是1。相反,如果包含对这个值引用的变量又取得了另外一个值,则这个值的引用次数就减1。当这个引用次数变成0时,则说明没有办法再访问这个值了,因而就可以将其所占的内存空间给收回来。这样,垃圾收集器下次再运行时,它就会释放那些引用次数为0的值所占的内存。
该方式会引起内存泄漏的原因是它不能解决循环引用的问题:

function sample(){
    var a={};
    var b={};
    a.prop = b;
    b.prop = a;
}

这种情况下每次调用sample()函数,a和b的引用计数都是2,会使这部分内存永远不会被释放,即内存泄漏。

低版本IE中有一部分对象并不是原生JS对象。例如,其BOM和DOM中的对象就是使用C++以COM(Component Object Model)对象的形式实现的,而COM对象的垃圾收集机制采用的就是引用计数策略。

因此即使IE的js引擎是用的标记清除来实现的,但是js访问COM对象如BOM,DOM还是基于引用计数的策略的,也就是说只要在IE中设计到COM对象,也就会存在循环引用的问题。

当一个DOM元素和一个原生的js对象之间的循环引用时:

var ele = document.getElementById("eleId");
var obj = {};
obj.property = ele;
ele.property = obj;
添加 obj.property = null;ele.property = null;即可解除原生JS对象与DOM元素之间的连接。

当闭包中创建循环引用时:

window.onload = function outerFunction(){
    var obj= document.getElementById("eleId");
    obj.onclick = function innerfunction(){
        console.log(obj.id);
    }
}

上面这个代码创建了一个作为obj元素处理程序的闭包,而这个闭包则又创建了一个循环引用。obj引用了document.getElementById("element"),而document.getElementById("ele  Id")的onclick方法会引用包括 obj 以内的外部环境中的变量,所谓“外部环境”包括了包含函数的整个活动对象,所以一定会包括 obj(即使闭包没有对 obj 进行直接的引用,例如上文程序中没有 obj.id 出现,包含函数的活动对象(obj)中也依旧会保存一个引用)。

可以改成下面这个:

window.onload = function outerFunction(){
    var obj= document.getElementById("element");
    var id = obj.id;//将obj副本保存于变量id中,则不会使obj元素处理程序的闭包创建循环引用
    obj.onclick = function innerfunction(){
        console.log(id);
    }
    ele = null;//手动断开 obj 对 document.getElemengById("element")的引用
}

介于js的垃圾回收机制,则建议如果当引用完大的对象后将其置为null。

标签:垃圾,obj,浅谈,回收,引用,var,浏览器,变量
From: https://www.cnblogs.com/sexintercourse/p/16603517.html

相关文章

  • 【web自动化】selenium根据浏览器版本下载对应的chromedriver
    1、使用国内的镜像地址https://registry.npmmirror.com/binary.html?path=chromedriver/ 2、通过simulation模拟用户点击来下载(只贴出部分方法)#!/usr/bin/envpython......
  • 浅谈MVVM开发思想
    IT流行语:程序=算法+数据结构。还有一句话,程序=输入数据->数据处理->输出数据。如果以编程语言理解这句话,算法是方法,数据结构就是变量的组织形式,那么这句话可以理解......
  • vue监听浏览器主动刷新
    mounted(){window.addEventListener('beforeunload',e=>this.beforeunloadHandler(e))//监听页面刷新触发事件},methods(){......
  • 禁止浏览器自动填充
    禁止浏览器自动填充如何禁止浏览器自动填充autocomplete属性规定输入字段是否应该启用自动完成功能方法一:设置autocomplete=“new-password”没错,autocomplete是可以控制......
  • 浅谈 Raft 分布式一致性协议|图解 Raft
    前言本篇文章将模拟一个KV数据读写服务,从提供单一节点读写服务,到结合分布式一致性协议(Raft)后,逐步扩展为一个分布式的,满足一致性读写需求的读写服务的过程。其中将配合引......
  • Harley浅谈Hadoop(HDFS)
     一、HDFS概述 1.1、HDFS产出背景及定义 1.1.1、HDFS产生背景   随着数据量越来越大,在一个操作系统存不下所有的数据,那么就分配到更多的操作系统管理的磁盘......
  • 浅谈 Exgcd 和同余问题
    \[\large\text{本以为学的是数学专题,实际上学的是}\]\[\huge\stackrel{\text{xuán}}{\textbf{数}}\textbf{学专题}\]玄学专题\(\Huge\textbf{1}\\small\text{Exgcd(扩......
  • 【DS】浅谈树状数组倍增
    无意中看到的一个小trick,便记录下来。引入给您一个数组,您需要实现以下操作和询问:\(\bullet\)插入一个数字\(x\)。\(\bullet\)查询排名为\(k\)的数\(x\)。......
  • 模拟浏览器滚动条持续向下滚动
    文件目录结构D:.chromedriver.exe浏览器向下滑动.py代码fromseleniumimportwebdriverimporttimeimportrandomdefroll_window_to_bottom(browser,......
  • openssh-浅谈openssl和openssh的升级
    最近项目上有服务器漏洞被扫描出来,是关于openssl的之前没怎么关注过这个问题,于是着手去了解了以下发现有些坑,分享下自己的经验。中间过程比较长,想省事的直接跳到第四节,......