Javascript ReferenceError和全局对象

Javascript ReferenceError和全局对象,javascript,window,referenceerror,global-object,Javascript,Window,Referenceerror,Global Object,在JavaScript中,浏览器窗口中的是全局对象,这意味着全局范围中定义的每个变量都是窗口的子对象。那么为什么我会得到这个结果: console.log(window.foo);//无错误,日志“未定义”。 console.log(foo);//未捕获引用错误:未定义foo。在第一个示例(window.foo)中,您正在访问window对象的属性。当您试图访问对象的不存在属性时,JavaScript返回“undefined”。它就是这样设计的 在第二个示例中,您直接引用了一个变量,由于它不存

在JavaScript中,浏览器
窗口中的
是全局对象,这意味着全局范围中定义的每个变量都是
窗口
的子对象。那么为什么我会得到这个结果:

console.log(window.foo);//无错误,日志“未定义”。
console.log(foo);//未捕获引用错误:未定义foo。
在第一个示例(window.foo)中,您正在访问window对象的属性。当您试图访问对象的不存在属性时,JavaScript返回“undefined”。它就是这样设计的

在第二个示例中,您直接引用了一个变量,由于它不存在,因此引发了一个错误


这就是JavaScript的设计和工作方式。

因为使用
window.foo
可以明确地查找
foo
对象的
foo
属性,而在后一个选项中不是这样。在后一个选项中,如果未定义
foo
,作为开发人员,您应该能够知道它未定义,并获得清晰的错误警告,而不是解释器自己将其设置为
undefined
(如第一种情况),这将导致意外的结果

var foo;
foo.bar; //TypeError (base value, foo, is undefined)
bar.baz; //ReferenceError (bar is unersolvable)
undefined.foo; //TypeError (base value is undefined)
foo; //ReferenceError
表示引用不存在的变量时出错。 尝试取消引用尚未声明的变量时引发ReferenceError

有关更多信息,请参阅本文:

引述上述文章:

如果引用的基值未定义,则该引用被视为不可解析。因此,如果点之前的值未定义,则属性引用是不可解析的。下面的示例将抛出ReferenceError,但它不会抛出,因为TypeError首先到达那里。这是因为属性的基值受制于CheckObjectImprovalible(ECMA 5 9.10到11.2.1),当尝试将未定义的类型转换为对象时,它会抛出TypeError

示例:

var foo;
foo.bar; //TypeError (base value, foo, is undefined)
bar.baz; //ReferenceError (bar is unersolvable)
undefined.foo; //TypeError (base value is undefined)
foo; //ReferenceError
根据定义,既不是属性也不是变量的引用是不可解析的,并且会引发引用错误,因此:

var foo;
foo.bar; //TypeError (base value, foo, is undefined)
bar.baz; //ReferenceError (bar is unersolvable)
undefined.foo; //TypeError (base value is undefined)
foo; //ReferenceError

在JavaScript中,您可以像这样动态地分配对象字段,因此
window.foo
几乎等同于
var foo在全局上下文中定义时,而突然调用
foo
会导致浏览器恐慌,因为它甚至不知道要查看哪个对象。请注意,如果您这样做:

//when in global context, 'var' sets a property on the window object
var foo;

console.log(foo);
//it will then also log `undefined` instead of throwing the error.

//if you then do:
foo = "abbazabba";

console.log(window.foo);
// it will return "abbazabba" 

window.foo
不等同于
var foo
@TimDown。你能再详细说明一下吗?也许在回答中?@TimDown&@gdoron好吧,这有点不真实-我的意思是window.foo在全局上下文中声明时等同于
var foo
。它仍然不完全等同。例如,可以删除已显式设置的全局对象的属性(在
window.foo=“bar”
之后,
delete window.foo;
删除
foo
属性并返回
true
),而不能删除变量(在
var foo=“bar”之后)
delete window.foo;
不执行任何操作并返回
false
)。我猜您正在控制台中尝试它,这会改变一些情况,因为控制台使用
eval()
,而使用
eval()执行的代码的行为与正常执行的代码略有不同。改为在测试页面中尝试。