1歉胶、let
6新加了let命令罕拂,用來聲明變量随闺,和var類似现拒。
但其聲明的變量只在let命令所在代碼塊內訪問,之外訪問不了灌砖。
{
let a=1;
var b=1;
}
console.log(a,b) // a not defined
它可用于for循環(huán)中
var a=[];
for(let i=0;i<10;i++){
a[i]=function(){
console.log(i):
}
}
a6;//輸出6
在每次for循環(huán)時i 都會一個新的變量璧函,i只在本地循環(huán)中可用。
它只在本地循環(huán)的塊中可訪問基显。
let 使用前必須先申明柳譬。
暫時性死區(qū):
只要塊級內有l(wèi)et命令,它所聲明的變量會綁定在這個塊上续镇,不受外部影響美澳。
var tmp = 123;
if (true) {
tmp = 'abc';
let tmp;
}
解析:這里全局有個tmp在塊內賦值了,后才創(chuàng)建的let tmp摸航。
在此塊內創(chuàng)建了let 制跟,但在申明前使用了它會報錯的。
es6明確規(guī)定酱虎,如果塊內存在let const ,這些變量會形成封閉作用域雨膨,凡是在聲明前使用都會報錯。
如果當全局內和塊內的let名稱一樣读串,先使用變量是不會向上級查找的聊记。
不允許重復聲明:
let在塊內不允許重復聲明同樣的變量。
Let a;
var a;
這時var 會報錯恢暖。
當然函數內的聲明不能和參數名一樣排监。
2、塊級作用域
為什么需要呢杰捂?
es5里只有全局作用域和函數作用域舆床,是沒有塊級作用域的。
問題1:
var tmp = new Date();
function f(){
console.log(tmp);
if (false){
var tmp = "hello world";
}
}
f() // undefined
執(zhí)行后會輸出未定義
原因是函數內的聲明變量提升,在訪問時會輸出未定義挨队,而不會到全局去找變量谷暮。
這樣內部變量覆蓋了對全局的訪問。
問題2:
for(var i=0;i<10;i++){}
console.log(i); //9
for 循環(huán)定義的i 在結束后還能訪問到盛垦。
所以let實現了塊級作用域湿弦。
function fn(){
let n=5;
if(true){
let n=10;
}
console.log(n)//5
}
因為有了塊作用域if內的let不會覆蓋到外部的。
es5允許塊作用域任意嵌套腾夯。
{{{let a=1;}}}
塊作用域的出現使得立即執(zhí)行函數沒那么重要了省撑。
函數中的function 函數會提升,會覆蓋掉全局的訪問俯在。這是es5時
es6是不會的竟秫。
聲明的let 在塊是可以訪問和修改的。
3跷乐、const命令
它聲明的是常量肥败。不需要改變的值。
聲明時必須要賦值的.
const的作用域和let一樣的愕提。
在聲明復合類型的常量時馒稍,變量名指向的是數據的地址.
const命令只保證常量指定的地址不變,并不保證地址指向的數據不變浅侨。
const a=[];
a.push(1);
a=[1,2]
賦值會報錯
可以將對象凍結纽谒,來實現不允許修改對象。
const a=Object.freeze({});
a.name=Xx;
添加屬性時會報錯如输。
上邊創(chuàng)建一個凍結的對象鼓黔,不可對其操作的。
4不见、跨模塊常量使用
const聲明的常量只能在當前代碼使用澳化,當然也可跨模塊使用
// constants.js 模塊
export const A = 1;
export const B = 3;
export const C = 4;
// test1.js 模塊
import * as constants from './constants';
console.log(constants.A); // 1
console.log(constants.B); // 3
// test2.js 模塊
import {A, B} from './constants';
console.log(A); // 1
console.log(B); // 3