严格模式下会直接报错的语法包括:with语句被禁用;arguments.callee/caller访问抛TypeError;给只读属性赋值、eval中声明变量、删除未声明变量、对象字面量重复属性名均报错。
启用严格模式后,JavaScript 会拒绝一些原本“宽容”的语法,让错误提前暴露。比如:with 语句完全禁用,arguments.callee 和 arguments.caller 访问抛出 TypeError,给只读属性赋值(如 NaN = 1)或在 eval 中声明变量也会立即失败。
常见踩坑点:
function f() { "use strict"; var x; x = 1; } —— 这样没问题;但若漏写 var/let/const,x = 1 会直接报 ReferenceError
delete x(删除未声明变量)在非严格模式返回 true,严格模式下抛 SyntaxError
{a: 1, a: 2})在严格模式下是语法错误严格模式不是全局开关,它只对当前作用域生效。最常用的是函数级启用:
"use strict";
function foo() {
// 这里是严格模式
}
function bar() {
"use strict";
// 这里也是严格模式
}
注意:
if 或 try 块内写 "use strict" —— 它必须是脚本或函数体的**首条可执行语句**(前面只能有注释).mjs 或 type="module" 的 script)默认启用严格模式,无需手动加 "use strict"
this 和变量绑定?这是最常被忽略的实际影响点。非严格模式下,顶层函数中的 this 指向 window(浏览器)或 global(Node.js);严格模式下,它为 undefined:
function foo() {
"use strict";
console.log(this); // undefined
}
foo();
变量绑定也更严格:
eval 不再能向外部作用域注入变量(eval("var x = 1") 不会让 x 出现在外层)function f(a, a) {} 在严格模式下是语法错误)arguments 不再与形参自动同步(function f(a) { "use strict"; a = 2; console.log(arguments[0]); } 输出仍是原值,而非 2)现代引擎(V8、SpiderMonkey)在严格模式下可以做更多优化:比如禁止 with 让作用域链更可预测,禁用 arguments.callee 避免隐藏的函数引用开销。更重要的是调试体验:
undefined 添加属性不再忽略)eval 注入的上下文"use strict" 可能导致某些规则误报真正麻烦的不是“要不要用”,而是混合使用:一个文件部分函数启用了严格模式,另一些没启,this 行为不一致、错误定位成本陡增。所以建议全项目统一,要么全部模块化(天然严格
),要么每个函数/脚本顶部明确声明。