gpt4 book ai didi

Javascript 全局范围分配

转载 作者:数据小太阳 更新时间:2023-10-29 05:52:41 26 4
gpt4 key购买 nike

我了解全局范围和 javascript 变量的问题及其普遍的不受欢迎;而且你到处都能找到它们。以下(在浏览器中)是等效的:

var foo = 3; // foo === 3, window.foo === 3
bazz = 10; // bazz === 10, window.bazz === 10

在全局范围内使用 var 关键字声明变量与在代码中任何地方不使用 var 声明它是一样的:您的变量被分配给根(窗口)对象。

我经常看到的一种技术(例如设置谷歌分析)是这样的:

var _gaq = _gaq || [];

... 我遵循的推理是,如果已声明 _gaq,则使用它,如果未声明,则将其创建为数组。它允许粗心的编码不会覆盖已分配给全局变量 _gaq 的任何值。

我不明白的是为什么这会引发错误:

_gaq = _gaq || [];

它们看起来和我一样:_gaq 应该采用 _gaq 的值或初始化为数组。但它会引发引用错误 - 我的问题是:它们为什么不同?

最佳答案

您永远无法读取 未声明的变量,这就是您尝试使用表达式 _gaq || 的原因[] 在最后一个例子中。

在这种情况下

 _gaq = _gaq || [];

_qaq 在评估右侧 (_gaq || []) 之前未声明,它会抛出错误。

这里是对这种情况下发生的事情的逐步解释:

赋值运算符在section 11.13.1中有描述。规范:

The production AssignmentExpression : LeftHandSideExpression = AssignmentExpression is evaluated as follows:

1. Let lref be the result of evaluating LeftHandSideExpression.
2. Let rref be the result of evaluating AssignmentExpression.
...

LeftHandSideExpression_gaqAssignmentExpression_gqa || [].

因此,首先对 _qaq 求值,结果为 unresolvable reference ,因为变量 _gaq 没有声明。此评估不会引发错误。

然后 _gqa || [] 被评估。这是一个 LogicalORExpression,在 section 11.11 中有描述。作为 LogicalORExpression ||逻辑与表达式。在这种情况下,左侧的 LogicalORExpression_gaq,右侧的 LogicalANDExpression[].
表达式的计算如下:

1. Let lref be the result of evaluating LogicalORExpression.
2. Let lval be GetValue(lref).
...

我们已经知道 lref 将是一个无法解决的引用,因为 _gaq 没有声明。那么让我们看看 GetValue 在做什么(在 section 8.7.1 中定义,V 是传递给 GetValue 的值):

1. If Type(V) is not Reference, return V.
2. Let base be the result of calling GetBase(V).
3. If IsUnresolvableReference(V), throw a ReferenceError exception.
...

如您所见,此过程的第三步抛出一个 ReferenceError 错误,该错误又通过评估赋值的右侧执行,这就是错误所在抛出。

那么,为什么 var _gaq = _gaq || 不会发生这种情况? []; ?

这一行:

var _gaq = _gaq || [];

实际上是

var _gaq;
_gaq = _gaq || [];

因为一个叫做 hoisting [MDN] 的东西.这意味着当 _gaq 被求值时,它不会产生一个不可解析的引用,而是一个值为未定义的引用.

(如果变量 _gaq 已经声明(并且可能有一个值),那么 var _gaq 将没有任何效果。)


如果您想从函数内部全局创建 _gaq,请通过引用 window显式执行此操作:

window._gaq = window._gaq || [];

关于Javascript 全局范围分配,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15388654/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com