前段時(shí)間開始了JS的學(xué)習(xí),第一個(gè)重要的知識(shí)點(diǎn)就是變量聲明及變量聲明提升疟呐。關(guān)于變量聲明,有這樣兩種代碼:
var a = 1;
console.log(a) // 1
a = 1 ;
console.log(a) // 1
var a = 1
东且,a = 1
都沒有報(bào)錯(cuò)的启具,那么這兩者區(qū)別在哪里呢?
首先珊泳,var
語(yǔ)句用于聲明變量鲁冯,而不使用var
直接賦值,則會(huì)創(chuàng)建一個(gè)全局變量色查,該變量是全局對(duì)象的一個(gè)屬性薯演。
如上面第2段代碼,在全局作用域下综慎,對(duì)非聲明的變量a
賦值涣仿,會(huì)創(chuàng)建一個(gè)全局變量a
,在瀏覽器中,a
為window
對(duì)象的一個(gè)屬性好港。
以上我們了解了非var a
的基本構(gòu)成愉镰,他們之間還有什么區(qū)別呢?
- 非聲明變量沒有變量提升钧汹,且只有在執(zhí)行賦值操作時(shí)才被創(chuàng)建
console.log(a) // ReferenceError: a is not defined
a = 1
console.log(a) // 1
- 聲明變量作用域限制在其聲明位置的上下文中丈探,非聲明變量在創(chuàng)建后是全局的
function f() {
a = 1
var b = 2
}
f() //執(zhí)行方法,創(chuàng)建變量
console.log(a) // 1
console.log(b) // ReferenceError: b is not defined
//這里可以看出拔莱,聲明變量的作業(yè)域是有限制的碗降,而非聲明變量在創(chuàng)建后會(huì)成為全局變量
- 聲明變量是它所在上下文環(huán)境的不可配置屬性(non-configurable property),非聲明變量是可配置的(例如非聲明變量可以被刪除)塘秦。
a = 2
var b = 2
var testa = Object.getOwnPropertyDescriptor(window, 'a')
var testb = Object.getOwnPropertyDescriptor(window, 'b')
// 在chrome下讼渊,使用Object.getOwnPropertyDescriptor方法對(duì)a和b 檢驗(yàn)
console.log(testa) // Object {value: 2, writable: true, enumerable: true, configurable: true}
console.log(testb) // Object {value: 2, writable: true, enumerable: true, configurable: false}
/*
Object.getOwnPropertyDescriptor()會(huì)返回對(duì)應(yīng)第一個(gè)參數(shù)的對(duì)象的屬性描述符(property description),
如果指定的屬性不在對(duì)象上尊剔,會(huì)返回undefined爪幻,
可以看出在全局作用域下,聲明變量和非聲明變量都為全局對(duì)象window的屬性须误。
其區(qū)別是聲明變量的configurable為true挨稿,非聲明變量的configurable為false。
*/
delete(a) // true 可以刪除
delete(b) // false 不可以刪除
console.log(a) // ReferenceError: a is not defined
console.log(b) // 2
// 根據(jù)configurable屬性京痢,非聲明變量a 可以被操作奶甘,而聲明變量a不可以
function ccc () {
c = 1
}
var ddd = {}
var testc = Object.getOwnPropertyDescriptor(window, 'c')
console.log(testc) // undefined
ccc()
var testc = Object.getOwnPropertyDescriptor(window, 'c')
var testd = Object.getOwnPropertyDescriptor(ddd, 'c')
console.log(testc) // Object {value: 1, writable: true, enumerable: true, configurable: true}
console.log(testd) // undefined
// 確認(rèn)非聲明變量在創(chuàng)建后,為全局對(duì)象的屬性
參考: