zoukankan      html  css  js  c++  java
  • 关于闭包

    这两天在苦苦钻研闭包,因为之前对闭包的接触并不多,于是大量在网上找资料。怕遗忘,登陆博客,记录日记

    什么是闭包,记得刚学习JS的时候,说闭包就是外部调用内部函数的变量。楼主当时比较浮躁,就以为是个很简单的东西,也就没有深究,但是随着,写的代码多了,感觉闭包真的非常有用。到目前为止,人生感悟用的最后就是匿名函数自调用。

    首先看我的两个案例,作用域和执行顺序。

    [javascript] view plaincopy
     
    1. <script>  
    2.      for (var i=0; i < 10; i++) {  
    3.            function aa(){  
    4.                alert(i);  
    5.            }  
    6.      };  
    7.      aa();//10  
    8.   
    9.   
    10.      for (var i=0; i < 10; i++) {  
    11.            function aa(){  
    12.                alert(i);  
    13.            }  
    14.             aa();//1...9  
    15.      };  
    16.        
    17. </script>  


    第一个弹出的是10,for循环执行完了,才调用函数aa(),这个时候i刚好等于10,于是alert(i)这个i引用了此时的i=10;

    第二个我们大家都知道,弹出的1...9,因为一边循环一边执行,这个我们应该都理解.第二个函数等同于下面这个匿名自调用函数.

    [javascript] view plaincopy
     
    1. for (var i = 0; i < 10; i++) {  
    2.           (function(j){  
    3.             alert(j)  
    4.           })(i)  
    5.    };  


     其实上面这个已经叫做闭包了。

     我自己的理解什么是闭包:能够让外部函数访问内部函数变量的过程叫做闭包。

    一般我们都是到外部函数是访问不了内部函数的。要访问淘宝开店我们只能通过闭包来访问,也就是返回内部函数。

    看下面这个:

    [javascript] view plaincopy
     
    1. var aa=99;  
    2.    function f1(){  
    3.        alert(aa);  
    4.    }  
    5.    alert(aa);//99  
    6.    
    7.    function f2(){  
    8.       var bb=99;  
    9.    }  
    10.    alert(bb);//error;  
    11.   
    12.    function f3(){  
    13.        cc=88;  
    14.    }  
    15.    f3();  
    16.    alert(cc);//88  

    定义了全局变量aa等于99,按照作用域的访问范围内部函数(访问)——外部——父级函数的规则(大家都叫链式作用域)。所有函数都可以访问aa;(说到这里其实我们所有的函数都是window对象下面的闭包,因为window是所有函数的父级);

    f1()执行后弹出了99;

    f2()执行后是个错误,因为在外部调用内部变量bb;

    f3()返回88,因为我没有用var声明,执行f3执行,让cc变成了全局变量,外部的都可以访问;

    如何让外部函数访问内部函数的变量呢?就是在函数里面再定义一个内部函数,然后返回就行了;

    [javascript] view plaincopy
     
    1. function f1(){  
    2.      var aa=99;  
    3.      var f2=function(){  
    4.          return function(){  
    5.               return aa;  
    6.        }();  
    7.    };  
    8.        return f2();  
    9. }  
    10. alert(f1());  

     这样外部函数就调用到了aa;这个时候其实内存并没有清除aa;因为闭包可以保存一些变量的值。

    [javascript] view plaincopy
     
    1.  function f1(){  
    2.       var aa=99;  
    3.       aadd=function(){aa+=1};  
    4.       var f2=function(){  
    5.           return function(){  
    6.                window.alert(aa);  
    7.         }();  
    8.     };  
    9.          return f2;//返回函数体  
    10.  }  
    11. var result=f1(); //引用F1函数 注意了这个时候f2等于被全局变量引用了,引发了内存一直保存着值;  
    12.     result(); //执行f1 99  
    13.     aadd(); //执行全局变量函数aadd;aa一直都保存在内存里面。  
    14.     result();//在执行f1  100  


    闭包差不多是这些了。下面来看看网上找的例子吧。

    [javascript] view plaincopy
     
    1. var name="The Window";  
    2.      var object={  
    3.            name:"kack",  
    4.            packname:function(){  
    5.             return function(){  
    6.                     return  this.name;   
    7.               }  
    8.   
    9.            }  
    10.      }  
    11.      alert(object.packname()());  
    12.   
    13.   
    14.     var name="The Window";  
    15.      var object={  
    16.            name:"kack",  
    17.            packname:function(){  
    18.               var that=this;  
    19.             return function(){  
    20.                     return  that.name;   
    21.               }  
    22.   
    23.            }  
    24.      }  
    25.      alert(object.packname()());  


    这个两个也是闭包,只不过多了个this指针的问题。一个是window,一个是object.所以答案一个是ths window。一个是kack;最后面我把函数给执行,内存释放了。

  • 相关阅读:
    每周必写
    每周必写
    每周必写
    感想及阅读内容
    阅读内容及感想
    每周感想和阅读内容
    每周感想及阅读内容
    每周感想及阅读内容
    分答
    每周感想及阅读内容
  • 原文地址:https://www.cnblogs.com/tiankong102/p/4249500.html
Copyright © 2011-2022 走看看