最近在学习闭包,想要真正了解闭包是怎么运行的,于是就遇见了JavaScript的GC机制,不知道这个机制,就不可能真的了解闭包。
其实不管什么语言,都有一套垃圾回收机制。为什么要有垃圾回收机制?因为内存,程序运行需要内存,如果没有垃圾回收,那么内存占用就会越来越高,轻点说会影响性能卡顿,严重的直接导致崩溃。
其实百度一下,JavaScript的GC机制,有很多文章,我就挑重点讲一下。JavaScript的垃圾回收原理就是:固定时间间隔,周期性的释放不在使用的变量所占内存。全局变量的生命周期直至浏览器卸载页面才会结束,局部变量只在函数的执行过程中存在。
我觉得重点就是全局变量的生命周期直至浏览器卸载页面才会结束,局部变量只在函数的执行过程中存在。当然,这可能讲闭包的时候用到,现在就讲GC。
垃圾回收有两个办法,给出的解释是:
标记清除
垃圾回收器会在运行的时候给存储在内存中的所有变量加上标记,然后去掉环境中的变量以及被环境中变量所引用的变量(闭包),在这些完成之后仍存在标记的就是要删除的变量了,因为环境中的变量已经无法访问到这些变量了,然后垃圾回收器相会这些带有标记的变量机器所占空间。
引用计数:
引用计数的策略是跟踪记录每个值被使用的次数,当声明了一个变量并将一个引用类型赋值给该变量的时候这个值的引用次数就加1,如果该变量的值变成了另外一个,则这个值得引用次数减1,当这个值的引用次数变为0的时候,说明没有变量在使用,这个值没法被访问了,因此可以将其占用的空间回收,这样垃圾回收器会在运行的时候清理掉引用次数为0的值占用的空间。
简单点来说就是有没有被引用,没有被引用的就会被回收,比如一个方法里面的变量,运行之后这个方法不再被使用就会被回收。
function fna() {
var a = 0;
}
var af = fna();
function fnb() {
var b = 0;
return b;
}
var bf = fnb();
a在fna执行之后跟全局已经没有关联了,就会被回收,b因为return给了全局变量bf,跟全局还关联着,就不会被回收。
JavaScript还能手动解除引用以便回收,比如上面的b被bf关联着,那么令bf = null;就能解除b的引用,在下次垃圾回收的时候,b就能被回收。
这就是简单的JavaScript垃圾回收机制,当然,学习这个只是为了闭包做铺垫,想了解更深层次的原理需要自行百度了。
欢迎关注Coding个人笔记 公众号