闭包和作用域

源码下载

局部变量和全局变量

  编程语言一般都有关于变量使用的规则,变量起作用的区域会有所限制,比如函数里面的变量在函数外不能直接调用。

 9        let S = 1;//全局变量S
10       for(let i = 0;i<10;i++){   //局部变量i
11           S -= i;
12       }
13        for(let i = 0;i<10;i++){   //局部变量i
14            for(let j = 1;j<11;j++){   //局部变量j
15                S += i*j;
16            }
17        }   

  变量S是全局变量,在for循环里面可以直接使用,每次执行S -= i;语句,全局变量S的变量值都会发生变化 局部变量证能在局部区域起作用,第10行和第13行的两个for循环都拥有变量i,他们的变量i只能在各自的作用域的起作用,超出大括号代码区域没有作用,即使重名也不会相互干扰。 第14行定义的for循环结构程序属于第13行定义的for循环定义的子区域,所以变量j不能与i重名,两个没有父子嵌套关系的函数里面变量名可以重名,子区域不能与父去与重名。 .一个函数、一个for循环结构、一个if结构程序都是一个独立的区域,有自己的局部变量。

  变量的作用域指的是变量的作用范围,根据作用范围不同分为局部变量和全局变量,局部变量也可以称为内部变量,全局变量也可以称为外部变量,在上面的程序中第13行变量i相对变量S而言是内部变量, 相对变量j而言是外部变量,也就是说称为内部或外部变量,都是有参照对象的,相比较而言,不是绝对的,因此大家在编程的时候知不知道这些名词不重要,关键能够明白变量的作用区域就行。

闭包

  实现函数外调用函数里面的变量。

不合法的写法

19       function fun() {
20           let a = 10;
21       }
22       let x =a;//函数里面的变量在函数外不能直接调用。 

闭包实现方法

24        function fun() {
25            let a = 10;
26            return function fun1() {   //定义一个辅助函数,用于返回局部变量a
27                return a;
28            }
29        }
30        let closure = fun();//closure指向fun1函数
31        let x = closure();//执行closure函数,把a赋值给变量x

  函数fun有一个变量a,如果想在函数外调用,赋值给变量x,就需要一个精巧的代码设计,第26到第28行通过关键字return就可以实现。先来看代码的执行,第30行调用函数fun,fun()执行得到的结果是function fun1(){return a;},通过操作符=,变量名closure关联到函数,就是说执行closure()可以调用函数 返回a的值。想在什么地方使用a,就直接执行函数closure。

匿名函数方式

  函数名fun1也可以不写,用第37行代码替换第26行代码,使用匿名函数模式,一般也是如此。主要是第30行的代码,相当于给第26行返回的函数重新命名closure。closure是函数对象新的地址索引。

35        function fun() {
36            let a = 10;
37            return function () {
38                return a;
39            }
40        }