Javascript 为什么隐式变量是可配置的,而显式变量和函数声明是不可配置的?

Javascript 为什么隐式变量是可配置的,而显式变量和函数声明是不可配置的?,javascript,Javascript,为什么隐式变量是可配置的,而显式变量和函数声明是不可配置的 foo='' console.log(Object.getOwnPropertyDescriptor(窗口'foo'))//可配置:true 变量条=“” console.log(Object.getOwnPropertyDescriptor(window,'bar'))//可配置:false只有在声明变量时,变量才会被放入当前范围或词法环境(变量名到它们所包含的值的内部映射)——也就是说,使用const、let或var 如果发生这种

为什么隐式变量是可配置的,而显式变量和函数声明是不可配置的

foo=''
console.log(Object.getOwnPropertyDescriptor(窗口'foo'))//可配置:true
变量条=“”

console.log(Object.getOwnPropertyDescriptor(window,'bar'))//可配置:false
只有在声明变量时,变量才会被放入当前范围或词法环境(变量名到它们所包含的值的内部映射)——也就是说,使用
const
let
var

如果发生这种情况,这些变量是不可删除的;一旦声明,它们就不能从作用域中删除。在顶层,将带有
var
的全局变量分配给全局对象。属性不能从全局对象中移除,因为标识符不能从全局范围中删除-因此,它是不可配置的


如果不声明变量,则在sloppy模式下为全局对象的属性赋值,但不为全局词汇环境创建标识符。它只是全局对象的一个属性,不是一个独立的变量名,因此它是可删除的(因此是可配置的)。

只有在声明变量时,变量才会被放入当前范围或词法环境(变量名到它们包含的值的内部映射)-也就是说,使用
const
let
,或
var

如果发生这种情况,这些变量是不可删除的;一旦声明,它们就不能从作用域中删除。在顶层,将带有
var
的全局变量分配给全局对象。属性不能从全局对象中移除,因为标识符不能从全局范围中删除-因此,它是不可配置的


如果不声明变量,则在sloppy模式下为全局对象的属性赋值,但不为全局词汇环境创建标识符。它只是全局对象的一个属性,不是独立的变量名,因此它是可删除的(因此是可配置的)。

JavaScript中没有隐式变量声明

在非严格模式下,如果未声明
foo
,无论我们是否处于全局环境中,则:

foo='bar'

相当于:

globalThis.foo=bar

这遵循向对象添加新属性的常规JavaScript行为。默认情况下,生成的属性是可配置的

鉴于全局上下文中的变量声明,如下所示:

var foo='bar'

…遵循不同的(
globalDeclarationInstallation
),其中一部分涉及将标识符添加到全球环境记录特有的
[[VarNames]]
内部插槽(in)。其具体目的似乎是允许区分全局对象上拟作为属性的属性和全局对象上拟作为变量的属性。作为此过程的一部分,
createglobalbarbinding
false
作为第二个参数调用,这意味着全局对象上的结果属性是不可配置的


因此,尽管在全局上下文中,
foo='bar'
var foo='bar'
都会在全局对象上生成一个属性,但一个是普通属性,另一个是具有特殊元数据和处理逻辑的普通属性。

JavaScript中没有隐式变量声明

在非严格模式下,如果未声明
foo
,无论我们是否处于全局环境中,则:

foo='bar'

相当于:

globalThis.foo=bar

这遵循向对象添加新属性的常规JavaScript行为。默认情况下,生成的属性是可配置的

鉴于全局上下文中的变量声明,如下所示:

var foo='bar'

…遵循不同的(
globalDeclarationInstallation
),其中一部分涉及将标识符添加到全球环境记录特有的
[[VarNames]]
内部插槽(in)。其具体目的似乎是允许区分全局对象上拟作为属性的属性和全局对象上拟作为变量的属性。作为此过程的一部分,
createglobalbarbinding
false
作为第二个参数调用,这意味着全局对象上的结果属性是不可配置的


因此,尽管在全局上下文中,
foo='bar'
var foo='bar'
都会在全局对象上生成一个属性,一个是普通属性,另一个是具有特殊元数据和处理逻辑的普通属性。

隐式创建的变量没有声明。这听起来像是对问题的重述?对于解释,实际上这是一个很好的解释
foo
window
的一个属性,因此您可以将其作为一个普通属性进行操作。然而,
bar
是一个声明的变量,它恰好也是
窗口的一个属性。因此,配置它将导致奇怪的行为-使
var
不可写意味着什么,它现在是常数了吗?但是,等等,它不可能是,因为它是一个
var
变量,所以如果不能写入它,它将不一致。好吧,我删除了“因为”,在编辑之前,您询问了“声明的隐式变量”,它不存在。不过,这也是一种解释。隐式创建的变量没有声明。这听起来像是对问题的重述?对于解释来说,实际上这是一个很好的解释