更多相关内容见博客 github.com/zhuanyongxi…

这一篇首先是打算证明一下《三个闭包实例理解闭包对内存的影响》

一共有9个例子,例7、8、9需要注意

只测试了Chrome,Chrome版本为67.0.3396.87(正式版本) (64 位)

例1



var a = 12;function fn() {  var a = new Array(10000000).join('x');  return function () {    var b = 1 + a;  }}var f = fn();

结果,占用内存。

图一

566a5df53eb0b385be2abc5fcb1de2f5be773cf3

例2


var oDiv = document.getElementById("div1");~function() {  var fn = function() {};  fn.data = new Array(10000000).join('x');  oDiv.  = fn;}();

结果同上图。如果把例子改成:


var oDiv = document.getElementById("div1");~function() {  var fn = function() {};  fn.data = new Array(10000000).join('x');  // oDiv.  = fn;}();

结果就是这样了,局部作用域中的函数fn被销毁了。

图二

140a8cecd1b97afb00def1ed807137db9006f8ed

例3


function fn(){  var a = new Array(10000000).join('x');  return function(){    var b = 1 + a;  }}fn();

结果同图二,返回函数没有被全局变量接住。

例4

这是一个延时销毁的例子。


function fn(){  var a = new Array(10000000).join('x');  return function(){    var b = 1 + a;  }}fn()();

先这样卡主断点:

fca41c03f98a79e871371ba1d5197c5083d799b9

测试内存结果同图一。

然后让程序运行完成,测试内存的结果就变成了图二。

例5


var fn;function foo() {  var a = new Array(10000000).join('x');  function baz() {    var b = 1 + a;  }  fn = baz;}foo();

结果同图一。

例6


function fn() {  var a = new Array(10000000).join('x')  return function () {    console.log("test");  }}var f = fn();

结果同图二,没有被返回的函数使用,销毁。

例7


function fn() {  var a = new Array(10000000).join('x')  var b = new Array(10000000).join('x')  return function () {    var b = 1 + a;  }}var f = fn();

结果同图一,被返回的函数使用的变量被储存了,没有被使用的被销毁了。

例8


function fn() {  var a = new Array(10000000).join('x');    function another() {    var b = 1 + a;  }    return function() {    console.log("test");  };}var f = fn();

结果同图一,变量没有被除返回函数之外的其他函数使用,依然会有内存被占用。

例9


function fn() {  var a = new Array(10000000).join('x');  return function(a) {    var b = 1 + a;  }}var f = fn();

结果同图二,没有被占用,变量a实际上被重新声明了。

总结

闭包环境中的变量会有存储在内存中的条件:返回了一个函数被使用(通常是被赋值给了一个外部的变量,例4是一个特殊的情况),且这个函数所在的执行环境中的变量被这个执行环境中的函数使用。

---- 20180625

文章最开始的版本,在返回函数中使用上级变量的方式是console.log(a),这里错了,console.log会把内容打到内存里面,所以在测试例4的时候会有问题。其他的结果虽然在修改之后没有变化,但是在开始时测试的思路不对。



原文发布时间为:2018年06月21日
原文作者:砖用冰西瓜
本文来源: 掘金 如需转载请联系原作者


收藏 打印