过什么七夕,来看闭包小萝莉🤪

405 阅读3分钟

这是我参与8月更文挑战的第2天,活动详情查看:8月更文挑战

emmm,今天七夕,像这种重大的节日,作为一名专注于单身工作研究的单身狗,怎可能会在今天出去逛gai看大街上看那些恩爱的男女给老夫心里造成伤害呢? 所以还是聊下闭包吧,这个每次我一看就会,一用就废的知识点,最近再看《javascript设计模式与开发实践》,这篇也算是读书笔记吧。

1.函数创造作用域:

这时候的函数,用书中的话说像是半透明玻璃,在函数里面可以看到外面的变量,而在函数外面则无法看到函数里面的变量。

	var a = "老子是外层的变量";
	var func1 = function(){
		var b = "人家是里面的变量👻";
		var func2 = function(){
			var c = "内存函数的变量";
			alert ( b ); // 输出:人家是里面的变量👻
			alert ( a ); // 输出:老子是外层的变量
		}
		func2();
		alert ( c ); // 输出:Uncaught ReferenceError: c is not defined
	};

	func1();

2.变量的生命周期:

尘归尘,土归土,及尽繁华,不过一掬细沙...扯得有点多,主要是内容如题,变量是有生命的,或者说有生命值的,就和打游戏一个道理,有的角色防高血厚,有的角色一碰,卒。

变量也是一样的,全局变量堪比太阳☀️,局部变量嘛,大致是狡兔死,走狗烹,类似于过河拆桥,卸磨杀驴,鞠躬尽瘁死而后已,用完就...😌,不过它过完了作为变量的灿烂的一生。

正常情况:

	var func = function(){
		var a = "函数内局部变量";
		alert(a);
	};
	func();
  • func函数中的变量a,会在函数执行完毕之后销毁。

特殊情况:

下面的例子中,变量af()执行完毕之后并没有消失,而是一直处在一个异次元空间里😱,一直活着...

😑:原因就是在var f = func执行后返回了一个匿名函数的引用,它可以访问到func()被调用时产生的环境,而上面说到的异次元空间就是这个了,存活的变量a也出于这个环境中。 而这个调用时候产生的环境,还能够被外界访问,这里面的局部变量,就有了不销毁的(借口)理由,也就有了下面的例子。

	var func = function(){
		var a = 1;
		return function(){
			a++;
			alert ( a );
		}
	};

	var f = func();

	f(); // 输出:2
	f(); // 输出:3
	f(); // 输出:4
	f(); // 输出:5

3.闭包的作用:

1.封装变量:

闭包可以把一些不需要暴露在全局的变量封装成私有变量

	//以避免这个变量在其他地方被不小心修改而引发错误。代码如下:
	var mult = (function(){
		var cache = {};
		return function(){
			var args = Array.prototype.join.call( arguments, ',' );
			if ( args in cache ){
				return cache[ args ];
			}
			var a = 1;
			for ( var i = 0, l = arguments.length; i < l; i++ ){
				a = a * arguments[i];
			}
			return cache[ args ] = a;
		}
	})();

//进一步封装,代码如下:
	var mult = (function(){
		var cache = {};
		var calculate = function(){ // 封闭calculate 函数
			var a = 1;
			for ( var i = 0, l = arguments.length; i < l; i++ ){
				a = a * arguments[i];
			}
			return a;
		};

		return function(){
			var args = Array.prototype.join.call( arguments, ',' );
			if ( args in cache ){
				return cache[ args ];
			}

			return cache[ args ] = calculate.apply( null, arguments );
		}

	})();

2.延长局部变量寿命:

img对象经常用于进行数据上报,如下:

	var report = function( src ){
	var img = new Image();
		img.src = src;
	};
	report( 'http://xxx.com/getUserInfo' );

这里存在的问题是,当report函数调用结束后,img局部变量随机被销毁,没没来得及发HTTP请求,请求就会丢失掉。

现在把img变量用闭包给它放到异次元空间里,便能解决请求丢失的问题:

	var report = (function(){
		var imgs = [];
		return function( src ){
			var img = new Image();
			imgs.push( img );
			img.src = src;
		}
	})();

对象以方法的形式包含了过程,而闭包则是在过程中以环境的形式包含了数据。

最后的最后,祝大家七夕快乐~!祝有天下有情人充成眷属,而我用于无比强大的前端技术,没错,我走火入魔了...