垃圾回收机制——把我回收了吧
目录
- js
- 标记清除
- 引用计数
- V8下的 分代式垃圾回收和增量标记算法
- 内存泄漏
js
JS 中的垃圾回收机制是为了预防内存泄漏,即当某个对象不再被使用时,垃圾回收机制会自动回收它占用的内存空间,以避免浪费计算机资源的情况。
主要通过标记清除和引用计数两种方式来实现。
标记清除
垃圾回收器会从根节点(通常是全局对象)开始遍历内存中的所有可访问对象,做上标记。之后,垃圾回收器将扫描内存中未标记的对象,并将其清除。
引用计数
引用计数算法会在内部维护一张表,记录每个值被引用的次数。当一个值被引用时,其引用计数加1;当一个值不再被引用时,其引用计数减1。当某个值的引用计数为0时,说明该值已不再被使用,可以被垃圾回收机制回收。
在实际开发中,标记清除算法常常用于大型项目或长时间运行的应用程序,而引用计数算法则主要应用于嵌入式系统或低级别的操作系统等环境下。
V8下的 分代式垃圾回收和增量标记算法
分代式垃圾回收
在新生代中,将内存分成新生代和老生代两个部分。新生代中的对象存活时间较短,而老生代中的对象则存活时间较长。将内存空间划分为两块,一块为存活对象的From空间,另一块为空闲的To空间,当From空间快满时,就会触发一次垃圾回收操作,将From空间中的存活对象复制到To空间中。经过多次复制后,如果某个对象存活时间较长,就会被移动到老生代中。
在老生代中,先遍历所有存活对象并做上标记,然后清除所有未标记的对象;在此基础上,将存活对象向一端移动,并清除掉其它空间的对象,以减少内存碎片。
增量标记算法
实现垃圾回收和程序执行的并行运行,以尽可能减少垃圾回收对程序执行的影响。增量标记算法将垃圾标记工作拆分成多个小任务,在各个任务之间穿插着执行程序代码,从而实现垃圾回收与程序执行的交替进行。
内存泄漏
哪些会造成
- 未清理定时器:如果在页面销毁前,没有清除掉相关定时器,那么这些定时器将一直运行,占用内存空间。
- 闭包:在JavaScript中,如果在一个函数内部创建了一个闭包,而该闭包又引用了外部函数作用域中的变量,那么这些变量将无法被垃圾回收机制回收。
- 循环引用:当两个对象相互引用时,如果它们之间的引用关系没有被恰当地打破,那么它们将无法被垃圾回收机制回收。
怎么看
Performance的Mempry
如果在使用过程中发现内存占用一直在增长,那么很可能存在内存泄漏问题。