闭包

Posted 郭郭郭牧鑫

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了闭包相关的知识,希望对你有一定的参考价值。

1、概念

闭包函数:声明在一个函数中的函数,叫做闭包函数。

闭包:内部函数总是可以访问其所在的外部函数中声明的参数和变量,即使在其外部函数被返回(寿命终结)了之后。

闭包的特点
1、让外部访问函数内部变量成为可能

2、局部变量会常驻在内存中

3、可以避免使用全局变量,防止全局变量污染

4、会造成内存泄漏(有一块内存空间被长期占用,而不被释放)

闭包就是可以创建一个独立的环境,每个闭包里面的环境都是独立的,并且互不干扰。闭包会发生内存泄漏,每次外部函数执行的时候,外部函数的引用地址不同,都会重新创建一个新的地址。但凡是当前活动对象中有被内部子集引用的数据,那么这个时候,这个数据不删除,保留一根指针给内部活动对象。大概意思就是说当外部函数运行结束甚至销毁时,局部的变量key=value,尽管key被垃圾回收机制给回收了,但是value仍不会被回收,会变成一个自由变量留下引用的指针。

/例子1/ 


function fn(){
  var a = 0;
  return function(){
        alert(a);
  }
}
var b = fn();
b();  //0

/例子2/ 

function fn(){
	var lll= 0;
	function fun(){
		lll++;
		console.log(lll);
	}
 return fun
}
var fun1 = fn();
fun1();//1
fun1();//2
fun1();//3
var fun2 = fn();
fun2();//1
fun2();//2
fun2();//3

这个例子,就是在返回函数中做了一个递增并打印的操作,把fn的返回函数给到fun1和fun2,当我向上面代码一样调用的时候呢,就会发现替他打印的不是12345,而是123123,那这是什么原因呢,这就回到了上边介绍的那句话:每次外部函数执行的时候,外部函数的引用地址不同,都会重新创建一个新的地址。所以说虽然fun1和fun2都是fn(),但是呢都创建了新地址,都是自己的,互不干扰。

/例子3/ 

var lll= 0;

function fn(){
    function fun(){
		lll++;
		console.log(lll);
	}
 return fun
}
var fun1 = fn();
fun1();//1
fun1();//2
fun1();//3
var fun2 = fn();
fun2();//1
fun2();//2
fun2();//3

这个跟例子2是一样的道理,只是变量的位置发生了改变,但是呢,对于内部的fun来说,变量是外部函数的局部变量和全局变量来说都是一样的。

/例子4/


function fn(){
	var a = 1;
	return fun(){
		return ++a;
	}
}
console.log(fn()());//2
console.log(fn()());//2
console.log(fn()());//2
var nfn = fn();
console.log(nfn());//2
console.log(nfn());//3
console.log(nfn());//4

/例子5/


(function() { 
  var m = 0; 
  function getM() { return m; } 
  function seta(val) { m = val; } 
  window.g = getM; 
  window.f = seta; 
})(); 
f(100);
console.info(g());   //100  闭包找到的是同一地址中父级函数中对应变量最终的值

(function(){ /* code */ })()是立即执行函数

/例子6/

var list = document.getElementsByTagName("li");
for(var i=0;i<list.length;i++){
  	(function(i){
      	 list[i].onclick = function(){
           	  console.log(i);
      	 };
  	})(i);
}

 

以上是关于闭包的主要内容,如果未能解决你的问题,请参考以下文章

scala编程——函数和闭包

由于lambda闭包或调度程序问题,程序可能会挂起

javascript 匿名函数及闭包----转载

10 个你可能还不知道 VS Code 使用技巧

Groovy闭包 Closure ( 闭包调用 | 闭包默认参数 it | 代码示例 )

Groovy闭包 Closure ( 闭包作为函数参数 | 代码示例 )