JavaScript var變量提升、let

  • JavaScript 引擎的工作方式:先解析代碼,獲取所有被聲明的變量,然后再一行一行地運行。就是所有的變量的聲明語句都會被提升到代碼頭部。
       var a = 'a';            // 聲明全局變量a全局變量a
        fun();                   // f是函數(shù),雖然定義在調(diào)用的后面,但是函數(shù)聲明會提升到作用域的頂部。 
        console.log(a);        // a=>'a',  此時是全局變量的a
        function fun() {
            console.log(a);      // 當前的a變量是下面變量a聲明提升后,默認值undefined
            var a = 'aa';
            console.log(a);      // a => 'aa'
        }
  //結(jié)果:undefined   aa  a
  • 函數(shù)聲明會在變量聲明上面
        var a='a'
        function a(){
            console.log(a)
        }
        a()
        //結(jié)果:a is not a function       
  • js引擎代碼解析:
        function a(){
            console.log(a)
        }
        console.log(a)
        var a//聲明過的變量不會重復聲明,所以在這時候,a是個函數(shù)
        a='a'//將function->'a'
        a()//這時候’a‘已經(jīng)賦值給a變量了,a()當然會報錯了
  • eg:
        fun()
        var fun = function(){
            console.log("aaa");
        }
        //結(jié)果: fun is not a function
        //解析
        var fun;//這時候fun->undefined
        fun(); //foo is not a function
        fun = function(){
            console.log("aaa");
        }
        //也可以理解成這樣
        console.log(a,'a')//a=>undefined那是因為,先聲明的變量,然后打印,最后賦值
        var a='333'
  • eg:
        console.log(fun);
        var fun='str';
        console.log(fun);
        function fun(){}
        console.log(fun);
結(jié)果:? fun(){}    str     str
        //解析
       function fun(){}
        var fun;//f聲明過的變量不會重復聲明
        console.log(fun)
        fun=10
        console.log(fun)//10
        console.log(fun)//10
  • 總結(jié):
    • 函數(shù)聲明會置頂
    • 變量聲明也會置頂
    • 函數(shù)聲明會在變量聲明上面(函數(shù)在變量上面)
    • 變量和賦值語句一起書寫,在js引擎解析時,會將其拆成聲明和賦值2部分,聲明置頂,賦值保留在原來位置
    • 聲明過的變量不會重復聲明

暫時性死區(qū):只要一進入當前作用域,所要使用的變量就已經(jīng)存在,但是不可獲取,只有等到聲明變量的那一行代碼出現(xiàn),才可以獲取、使用該變量。

let(提一下let)

  • 以前,我們都是用var來聲明變量,而且JS只有函數(shù)作用域、全局作用域,沒有塊級作用域,所以{}限定不了var聲明變量的訪問范圍。
     {
            var a='a-var'
        }
        console.log(a)//a-var
        {
            let b='b-let'// b變量只在 花括號內(nèi)可獲取
            console.log(b)//b-let
        }
        console.log(b)//b is not defined
  • let/const:不存在變量提升。要求必須 等let/const聲明語句執(zhí)行完之后,變量才能使用,否則會報錯。
  • 在代碼塊內(nèi),let命令聲明變量之前,該變量都是不可用的,稱為“暫時性死區(qū)”
  • eg:
       console.log(a)//undefined
        console.log(b)//報錯
        var a='a'
        let b='b'
  • eg:
       var a = 10;
        { 
            console.log(a)//10
            var a = 6;
            console.log(a)//6
        }
        console.log(a)//6
        var a = 10;
        {
            // console.log(a)//報錯,因為let不變量提升,暫時性死區(qū)
            let a = 6;
            console.log(a)//6

        }
        console.log(a)//10

  • 不可重復聲明
      {
            let b='b-let'
            let b='same-b'//報錯 Identifier 'b' has already been declared
        }

       //看下面例子,為什么我同時聲明了兩次q,卻沒有報錯。因為for 用let聲明q跟,for循環(huán)體里面用let聲明的q不在同一個塊級作用域里面
       // {
        //     let q=0
        //     {
        //         let q=12
        //         console.log(q)
        //     }
        //     ……
        // }
       for(let q=0;q<5;q++){
            let q=12
            console.log(q)// 12
       }
  • let和var的區(qū)別
    1. 通過var聲明的變量沒有塊作用域,在塊{ }內(nèi)聲明的變量可以從塊之外進行訪問。通過let聲明的變量擁有塊作用域,在塊{ }內(nèi)聲明的變量無法從塊外訪問
    2. 通過var重新聲明變量會帶來問題,在塊中聲明變量也將重新聲明塊外的變量,覆蓋塊外的變量。通過let重新聲明的變量不會重新聲明塊外的變量,會重新聲明一個有塊作用域的變量
    3. var會變量提升。let沒有變量提升,變量會從塊的開頭一直處于“暫時性死區(qū)”,直到聲明為止。
    4. 通過 var 定義的全局變量屬于 window 對象。通過 let 定義的全局變量不屬于 window 對象
  • let和var的共同點
    1. 在函數(shù)內(nèi)聲明變量時,使用 var 和 let 很相似,它們都有函數(shù)作用域
    2. 在塊外聲明,var 和 let它們都擁有全局作用域
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容