1. 程式人生 > >js:作用域總結1

js:作用域總結1

先說幾個概念:

   1、js程式碼從上往下執行 

   2、變數提升:

     變數提升是瀏覽器的一個功能,在執行js程式碼之前,瀏覽器會給js一個全域性作用域叫window,window分兩個模組,一個叫記憶體模組,一個叫執行模組,記憶體模組找到當前作用域下的所有帶var和function的關鍵字,執行模組執行js程式碼,從上到下執行,遇到變數就會通過記憶體地址去查詢這個變數,有和沒有這個變數。有這個變數就會看賦值沒賦值,如果賦值就是後面的值,如果沒有賦值就是undefined,如果沒有找到就說這個變數 is not defined。

   3、作用域鏈:

      

當函式內部的變數被使用時,首先會在自己的私有作用域下查詢是否有這個變數,如果有就使用,如果沒有就會向上一級(父級)查詢,父級有就使用父級的,如果沒有就繼續向上一級找,有就使用,沒有就接著往上找,直到window,window有就用,沒有就是is not defined。我們管這種查詢機制叫做作用域鏈。

 

 

一、簡單的小案例:

    1、

      var a = 12;

    function fn(){

      console.log(a);  //undefined

      var a = 45;

      console.log(a);  //45

    }

     2、

      function fn(){

      console.log(11);

      function ff(){

        console.log(22);

      }

      ff();

    }

    fn()  //11

    ff()  // ff is not defined

     3、

       var   a = 123;
    function  fun(){
     alert(a)  //123
    }
    fun();      //私有作用域下沒有宣告變數a,就在父級找,有就直接使用。

     4、

       var   a = 123;
    function   fun(){
      alert(a);  //123    私有作用域裡並沒有宣告變數a,所以就在父級找,有就直接使用。
      a = 456;
     }
     fun()
     alert(a)  //456      fun()裡改變了全域性變數a的值

     5、

       var   a = 123;
    function   fun(a){
      alert(a);  //undefined    這裡有形參,但是並沒有傳實參 
      a = 456;    //給引數賦值
    }
    fun();
    alert(a)  //123    全域性變數a

     6、

       var   a = 123;
       function    fun(a){
        alert(a);  //123      這裡傳了固定的引數123
        a = 456;
       }
       fun(123)
       alert(a)  //123

     7、

       var   a = 12;
    function   fn(){
      console.log(a)  //undefined      程式碼從上往下執行,記憶體模組只定義,不賦值。
      var   a = 45;
       console . log(a)  //45
    }
    fn()

     8、

       function test(a,b){
         console . log(b)  //function b(){}       function關鍵字,在記憶體模組裡面宣告和定義同時進行
         console . log(a)  //1   
         c=0;
         a=3;
         b=2;
         console . log(b);    //2
         function   b(){ }
         function   d(){ }
         console . log(b)    //2
       }
       test(1)

     9、

       function   test(a,b){
         console . log(a)  //function  a(){}  覆蓋了實參
         console . log(b)  //undefined
         var   b=234;
         console . log(b)  //234
         a=123;
         console . log(a)  //123
         function   a(){ }
         var   a;
         b=234;
         var   b=function (){ }
         console . log(a);  //123
         console . log(b) //function
       }
       test(1)

       

二、阿里面試:

    var a = 100;

    function testResult(){

      var b = 2 * a;

      var a = 200;

      var c = a / 2;

      alert(b);

      alert(c);

    }

    

 

三、自呼叫函式:

    +function(){

      console.log(a);

      var a = 5;

      function a(){}

      console.log(a);

      function b(){}

      b = 6;

      console.log(b);

      var c = d = b;

    }()

    console.log(d);

    console.log(c);

注:自呼叫函式沒有變數提升!