亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Js中var,let,const的區(qū)別你知道嗎

 更新時(shí)間:2023年02月08日 10:12:26   作者:Cirrod  
眾所周知在Javascript中,var、let、const都可用于變量聲明,但是之前沒有梳理過它們之間的區(qū)別,下面這篇文章主要給大家介紹了關(guān)于Js中var,let,const區(qū)別的相關(guān)資料,需要的朋友可以參考下

一:區(qū)別:

1、var聲明的變量屬于函數(shù)作用域,而let和const聲明的變量屬于塊級(jí)作用域;(js作用域在上篇文章) 

2、var聲明的變量存在變量提升,而let和const沒有

3、var聲明的變量可以重復(fù)聲明,而在同一塊級(jí)作用域,let變量不能重新聲明,const常量不能修改(對(duì)象的屬性和方法,數(shù)組的內(nèi)容可以修改)

二:var聲明的作用域

1. 使用var聲明的變量,這個(gè)變量屬于當(dāng)前的函數(shù)作用域,如果變量的聲明在任何函數(shù)外,那么這個(gè)變量就屬于全局作用域

var a = 1; //此處聲明的變量a為全局變量
function foo(){
   var a = 2;//此處聲明的變量a為函數(shù)foo的局部變量
   console.log(a);//2
}
 
foo();
console.log(a);//1

2.如果在聲明變量時(shí),省略 var 的話,該變量就會(huì)變成全局變量,如全局作用域中存在該變量,就會(huì)更新其值

var a = 1; //此處聲明的變量a為全局變量
function foo(){
   a = 2;//此處的變量a也是全局變量
   console.log(a);//2
}
 
foo();
console.log(a);//2

三:var聲明的變量提升

1.var的聲明會(huì)在js預(yù)解析時(shí)把var的聲明提升到當(dāng)前作用域的最前面,意思是是指無論 var 出現(xiàn)在一個(gè)作用域的哪個(gè)位置,這個(gè)聲明都屬于當(dāng)前的整個(gè)作用域,在其中到處都可以訪問到。只有變量聲明才會(huì)提升,對(duì)變量賦值并不會(huì)提升

console.log(a);//undefined
var a = 1;

相當(dāng)于執(zhí)行以下代碼

var a;
console.log(a);//undefined
a = 1;

四、let聲明

1.let 聲明的變量具有塊作用域的特征。

2.在同一個(gè)塊級(jí)作用域,不能重復(fù)聲明變量。

function foo(){
    let a = 1;
    let a = 2;//Uncaught SyntaxError: Identifier 'a' has already been declared
}

3.let 聲明的變量不存在變量提升,換一種說法,就是 let 聲明存在暫時(shí)性死區(qū)(TDZ)。

let a = 1;
console.log(a);//1
console.log(b);//Uncaught ReferenceError: b is not defined
let b = 2;

(此時(shí)變量b的聲明不會(huì)提升到當(dāng)前作用域的前面)

五:徹底區(qū)分var和let聲明變量(作用域區(qū)別)

1.var聲明

for (var i = 0; i < 10; i++) {
    setTimeout(function(){
        console.log(i);
    },100)
};

(1.此時(shí)的var聲明的變量i屬于函數(shù)作用域,聲明又不在函數(shù)里,所以i屬于全局變量

2.此時(shí)的定時(shí)器函數(shù)屬于異步函數(shù),隔100毫秒才會(huì)執(zhí)行,而這100毫秒的時(shí)間內(nèi),for循環(huán)已經(jīng)循環(huán)結(jié)束,全局變量i已經(jīng)為10

3.相當(dāng)于代碼執(zhí)行

    {
       var i = 0;
      // 第一次循環(huán)
      {
        setTimeout(() => {
          //延時(shí)器屬于異步函數(shù),不會(huì)立即執(zhí)行,
          //經(jīng)過1s后,循環(huán)已經(jīng)結(jié)束,全局變量i已經(jīng)變成10
          console.log(i);
        }, 1000)
        i++
      }
      // 第二次循環(huán)
      {
        setTimeout(() => {
          //var聲明的變量i沒有塊級(jí)作用域,所以可以訪問第一次循環(huán)體內(nèi)的變量i,
          //同樣,1s后,循環(huán)已經(jīng)結(jié)束,全局變量i已經(jīng)變成10
          console.log(i);
        }, 1000)
        i++
      }
      .....
    }

最后代碼的執(zhí)行后,會(huì)在控制臺(tái)打印出10個(gè)10)

ps:主要的原因是var聲明的變量的沒有塊級(jí)作用域

2.let 聲明

使用閉包原理解決上例中var聲明變量的不具有塊級(jí)作用域的問題:

    for (var i = 1; i <= 5; i++) {
      //i=0  第一輪循環(huán)
      (function (i) {
        // 立即執(zhí)行函數(shù)執(zhí)行,形成一個(gè)私有的函數(shù)上下文
        //形參i是屬于立即執(zhí)行函數(shù)的局部變量,第一輪循環(huán)時(shí)相當(dāng)于let i=0
        //由于立即執(zhí)行函數(shù)的參數(shù)i被下一級(jí)的延時(shí)器回調(diào)函數(shù)上下文所引用,所以會(huì)產(chǎn)生閉包,
        //  從而形成塊級(jí)作用域,保護(hù)了每一次循環(huán)的i,也就是閉包的特點(diǎn):變量私有化
 
        setTimeout(() => {
          // 延時(shí)器回調(diào)函數(shù)執(zhí)行,也會(huì)形成一個(gè)私有的函數(shù)上下文
          console.log(i);//由于當(dāng)前延時(shí)器回調(diào)函數(shù)上下文引用了
          // 上一級(jí)立即執(zhí)行函數(shù)的參數(shù)i(立即執(zhí)行函數(shù)的局部變量),
          //所以此時(shí)會(huì)產(chǎn)生閉包,立即執(zhí)行函數(shù)的參數(shù)i會(huì)一直保存在內(nèi)存中供延時(shí)器回調(diào)函數(shù)使用
        }, 5000)
      })(i)//把每一輪循環(huán)全局的i的值作為實(shí)參傳遞給立即執(zhí)行函數(shù)的私有上下文,第一輪傳遞的是0
 
    }

使用let聲明的變量具有塊級(jí)作用域

for (let i = 0; i < 10; i++) {
     // 每一輪都會(huì)形成一個(gè)私有的塊級(jí)作用域,并且有一個(gè)私有的變量i,分別存儲(chǔ)每一輪循環(huán)的索引
    setTimeout(function(){
        console.log(i);
    },100)
 
};

 PS:這是因?yàn)殚]包的機(jī)制,但是因?yàn)閘et的塊作用域是瀏覽器底層機(jī)制實(shí)現(xiàn)的,比我們自己創(chuàng)建的閉包性能要好一些

代碼執(zhí)行后,則該代碼運(yùn)行后,就會(huì)在控制臺(tái)打印出0-9. )

 六:const 聲明

1.const 聲明方式,除了具有 let 的上述特點(diǎn)外,其還具備一個(gè)特點(diǎn),即 const 定義的變量,一旦定義后,就不能修改,即 const 聲明的為常量。

const a = 1;
console.log(a);//1
a = 2;
console.log(a);//Uncaught TypeError: Assignment to constant variable.

2.但是,并不是說 const 聲明的變量其內(nèi)部?jī)?nèi)容不可變,如:

const obj = {a:1,b:2};
console.log(obj.a);//1
obj.a = 3;
console.log(obj.a);//3

所以準(zhǔn)確的說,是 const 聲明創(chuàng)建一個(gè)值的只讀引用。但這并不意味著它所持有的值是不可變的,只是變量標(biāo)識(shí)符不能重新分配。

(我的理解是如果是簡(jiǎn)單數(shù)據(jù)類型,const聲明的變量保存的值就是變量的值,是不可以修改,但如果是復(fù)雜數(shù)據(jù)類型(對(duì)象,數(shù)組等)const只是保存的是復(fù)雜數(shù)據(jù)類型的地址,只是確保地址不可變,但地址指向的內(nèi)容是可以變的)

總結(jié)

最后,因?yàn)閘et和const是es6的新特性,let和const的出現(xiàn)就是為了解決var的各種問題,強(qiáng)烈建議大家寫js代碼都用let和const聲明變量和常量! 

到此這篇關(guān)于Js中var,let,const區(qū)別的文章就介紹到這了,更多相關(guān)Js中var,let,const區(qū)別內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

最新評(píng)論