javascript - JavaScript 严格模式下 "this"的行为不一致

标签 javascript this strict

更新

为了清楚起见:@FelixKing:是的,我期望 this调用 window.foo() 时仍然未定义,原因如下:因为,在 JavaScript 中:

function foo()
{
    console.log('I am a function');
}

(几乎)与以下内容相同:

var foo = function()
{
    console.log('I am a function');
}

foo === window.foo评估为 true,我希望他们都表现得相似。如果函数是变量,并且 JS 回退到全局对象(在函数 x 内部,未声明变量但您使用它,则 JS 冒泡 遍历所有作用域,直到全局对象,直到它找到有问题的变量,或者在全局级别上创建它),如果指定 window 应该没有关系。是否预先反对。然而,当你这样做时,行为会发生变化,这是我没有预料到的。
我有一种直觉为什么会出现这种情况(我正在定义方法,而不是变量)但话又说回来,对于全局对象来说,它们之间几乎没有什么区别。 var c = 'Variable'; console.log(window.c === c);记录 true 等...但我想知道实际上的区别是什么,以及它是如何工作的(在所有级别)。

我准备好接受这一点foo.apply(this,[]);foo.apply(window,[]);让你强制this指向全局对象,但不是window.foo(); 。如果严格是为了屏蔽全局对象,我会说这会留下后门大开。例如,我偶尔会发现自己根据变量的值调用函数。为此,我使用 window[myVar](); ,无论严格与否,这意味着 this 指向全局对象,而如果我直接调用该函数则不会。在我看来,这是一种不一致。


我遇到了 this 的一些奇怪行为严格模式下的关键字。别误会我的意思我知道thisundefined in strict functions 。我觉得令人困惑的是 this可以被迫指向全局对象(或任何其他对象,就此而言),有效地破坏严格模式提供的安全网。这还有其他含义。考虑这段代码:

'use strict';//using strict everywhere
(function(Global)
{
    var closureObject = {};
    Global.foo = function()
    {
        closureObject.setIn = closureObject.setIn || 'Set in foo';
        console.log(this);
        console.log(this === Global);
        bar();
        bar.apply(this);
        return (this !== Global ? this : undefined);
    };
    Global.bar = function()
    {
        closureObject.setIn = closureObject.setIn || 'set in bar';
        console.log(this);
        return (this !== Global ? this : undefined);
    };
})(this);
var undef = (Math.ceil(Math.random()*10)%2 ? foo() : bar());
foo();//undefined --- false​​​​​​​​​​​​​​​​​ --- undefined --- undefined
window.foo();//Window --- true --- undefined --- window
foo.apply(this,[]);//same as window.foo

这同样适用于自定义对象:

function Foo(n)
{
    this.name = n;
}
Foo.prototype.func = foo;//or window.foo
//other objects:
var d = new Date();
foo.apply(d,[]);//Date --- false --- undefined --- date

在我看来,这可能是黑客攻击和陷阱的根源。更重要的是:这使得确定调用来自哪里变得相当困难:if foo()从全局对象( window.foo(); )调用,该上下文当然不会传递给 bar ,除非bar使用 bar.apply(this,[]); 调用

我可能想要一种简单、安全、可靠的方法来确定调用者上下文的原因很简单:我使用闭包来避免那些讨厌的全局变量,但同时我正在设置几个充当事件处理程序的函数。
我知道不使用严格模式或设置全局是很容易解决的问题,但严格模式将继续存在,我喜欢它给聚会带来的东西(嗯,大部分)。我坚信这就是 JS 发展的方式,我不想因为不想打扰 strict 而发现自己为自己的破损代码哭泣。 。这可能不会太快发生,但我只是想让我的知识保持最新。

我已阅读 strict 上的 MDN 页面以及 John Resig 的博客文章,我观看了相当多的 DC 视频并阅读了他的很多文章,但我还没有找到对我上面描述的行为的明确解释。我还没有通读整个 ECMAScript 标准(天哪,那东西太干了,它可能会耗尽撒哈拉沙漠的水),但也许这里有人可以给我指出正确的方向,帮助我更好地理解这一点。

最佳答案

我不确定我是否正确地阅读了您的问题,但似乎您对 func.apply(context, argument) 可以采用 的事实感到困难context 作为参数,然后由函数内的 this 引用。

我认为传递上下文是必要的,没有它 JavaScript 就无法正常工作。

在我的脑海中,由于没有super,正确使用继承的唯一方法是使用BaseClass.prototype.baseFunction.apply(this,arguments).

删除该功能将创建一种与当今 JavaScript 非常不同的语言,而这不是严格模式的含义。

关于javascript - JavaScript 严格模式下 "this"的行为不一致,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12250609/

相关文章:

javascript - 表单验证中的错误消息未按预期显示

javascript - 如何使用 React.js 将状态属性传递给构造函数中的子组件?

javascript - 在严格模式下实现智能/自覆盖/惰性 setter/getter

javascript - 带有 http、header、meta 和 body 的 JSON 响应

javascript - 在警报消息后使用 PHP 重定向到 HTML 页面

java - 从 Google Chrome 的开发者工具获取信息

javascript - 需要帮助理解 JavaScript 对象

javascript - javascript 中的 'this' 指的是什么?

haskell - 惰性评估和严格评估 Haskell

css - 粘性页脚、页眉和 100% 高度内容