为什么严格模式会使如此简单的操作如此不同?
Why does strict mode make such simple actions such different?
有一个极其简单的算法,根据 "use strict"
.
的存在,它在两种情况下的工作方式出奇地不同
案例 1:
如果func()
声明在严格模式下,那么控制台记录原始
"use strict";
// strict mode is on
Object.prototype.func = function() { return this; } // do nothing with the object
console.log( (4).func() ); // 4; primitive
案例二:
如果func()
声明在严格模式之外,那么控制台记录相同值的对象
// strict mode is off
Object.prototype.func = function() { return this; } // do nothing with the object
"use strict";
console.log( (4).func() ); // Number {[[PrimitiveValue]]: 4}; object
这种差异的根源是什么?这种转换的原因是什么?
如此简单的动作,在严格模式的各种状态下,怎么会有如此不同?
this
不被装箱是严格模式的有意改动之一。这可以防止 JavaScript 代码访问原语,从而简化它以证明 JavaScript 片段是无害的。我猜它也有轻微的速度改进。
详情请参考MDN。
在此特定示例中,任何不是对象、函数或数组的东西都是原语。 (函数和数组在技术上是对象。)原始值的问题是你不能有方法。所以,你不能做类似 "hello world".toUpperCase()
的事情。一般来说,程序员喜欢拥有与他们正在使用的任何类型的对象相关的方法,而不是大量全局可用的函数(例如 parseInt
)。
因此,JavaScript 有 String
、Number
和其他具有 toUpperCase
、toLowerCase
和 toString
方法的对象。当我们在字符串或数字上调用这些方法之一时,JavaScript 包装在相应的对象中,调用该方法并 returns 原始结果。这一切都在幕后发生,我们通常不必担心。
除非它不起作用——就像在你的例子中一样。 JavaScript 的早期版本中出现了一些错误,但由于向后兼容,我们无法真正更改这些内容。如果我在 1995 年创建了一个使用 JavaScript 的网站,然后在 1997 年更改了规则,我的网站就会突然崩溃。
也就是说,很多错误都有合理的解决方案,如果我们可以选择一些额外的安全措施,那就太好了。较旧的浏览器看到孤独的字符串 "use strict" 并忽略它。较新的浏览器会看到这一点并选择加入一组新规则,概述 here。
有一个极其简单的算法,根据 "use strict"
.
案例 1:
如果func()
声明在严格模式下,那么控制台记录原始
"use strict";
// strict mode is on
Object.prototype.func = function() { return this; } // do nothing with the object
console.log( (4).func() ); // 4; primitive
案例二:
如果func()
声明在严格模式之外,那么控制台记录相同值的对象
// strict mode is off
Object.prototype.func = function() { return this; } // do nothing with the object
"use strict";
console.log( (4).func() ); // Number {[[PrimitiveValue]]: 4}; object
这种差异的根源是什么?这种转换的原因是什么?
如此简单的动作,在严格模式的各种状态下,怎么会有如此不同?
this
不被装箱是严格模式的有意改动之一。这可以防止 JavaScript 代码访问原语,从而简化它以证明 JavaScript 片段是无害的。我猜它也有轻微的速度改进。
详情请参考MDN。
在此特定示例中,任何不是对象、函数或数组的东西都是原语。 (函数和数组在技术上是对象。)原始值的问题是你不能有方法。所以,你不能做类似 "hello world".toUpperCase()
的事情。一般来说,程序员喜欢拥有与他们正在使用的任何类型的对象相关的方法,而不是大量全局可用的函数(例如 parseInt
)。
因此,JavaScript 有 String
、Number
和其他具有 toUpperCase
、toLowerCase
和 toString
方法的对象。当我们在字符串或数字上调用这些方法之一时,JavaScript 包装在相应的对象中,调用该方法并 returns 原始结果。这一切都在幕后发生,我们通常不必担心。
除非它不起作用——就像在你的例子中一样。 JavaScript 的早期版本中出现了一些错误,但由于向后兼容,我们无法真正更改这些内容。如果我在 1995 年创建了一个使用 JavaScript 的网站,然后在 1997 年更改了规则,我的网站就会突然崩溃。
也就是说,很多错误都有合理的解决方案,如果我们可以选择一些额外的安全措施,那就太好了。较旧的浏览器看到孤独的字符串 "use strict" 并忽略它。较新的浏览器会看到这一点并选择加入一组新规则,概述 here。