全局块级绑定

letconst不同于var的另一个方面是在全局作用域上的表现。当在全局作用域上使用var时,它会创建一个新的全局变量,并成为全局对象(在浏览器中是window)的一个属性。这意味着使用var可能会无意覆盖一个已有的全局属性,就像这样:

// 在浏览器中
var RegExp = "Hello!";
console.log(window.RegExp);    // "Hello!"

var ncz = "hi!";
console.log(window.ncz);     // "hi!"

尽管全局的RegExp是定义在window上的,它仍然不能防止被var重写。这个例子声明 了一个新的全局变RegExp而覆盖了原有对象。类似的,ncz定义为全局变量后就立即成为了window的一个属性。这就是JS通常的工作方式。

然而若你在全局作用域上使用letconst,虽然在全局作用域上会创建新的绑定,但不 会有任何属性被添加到全局对象上。这也就意味着你不能使用letconst来覆盖一个全 局变量,你只能将其屏蔽。这里有个范例:

// 在浏览器中
let RegExp = "Hello!";
console.log(RegExp);                     // "Hello!"
console.log(window.RegExp === RegExp);   // false

const ncz = "hi!";
console.log(ncz);                        // "hi!"
console.log("ncz" in window);            // false

此代码的let声明创建了RegExp的一个绑定,并屏蔽了全局的RegExp。这表示window.RegExpRegExp是不同的,因此全局作用域没有被污染。同样,const声明创建了ncz的一个绑定,但并未在全局对象上创建属性。当你不想在全局对象上创建属性时,这种特性会让letconst在全局作用域中更安全。

若想让代码能从全局对象中被访问,你仍然需要使用var。在浏览器中跨越帧或窗口去访问代码时,这种做法非常普遍。

results matching ""

    No results matching ""