暂时性死区(TDZ)是let/const声明在词法作用域中自然形成的区域,从作用域起始到变量声明执行完毕前,访问该变量会抛出ReferenceError。

JS 中的暂时性死区(Temporal Dead Zone,TDZ)不是手动“产生”的,而是 let 和 const 声明本身在词法作用域中自然形成的区域——从块级作用域开始到该变量实际声明语句执行完成前的这段范围。在这段区域内访问变量,会抛出
ReferenceError</code。</p> <H3>TDZ 的触发条件:用 let/const 声明但尚未初始化</H3> <p>只要使用 <code>let或
const 声明变量,JS 引擎就会为它创建一个 TDZ。这个区域从进入作用域(比如函数体或代码块开头)就开始,直到声明语句执行完毕(即赋值完成)才结束。
将一个或多个视频上传至YouTube。当用户想“上传到YouTube”“发YouTube”“批量上传”“upload to YouTube”“post videos to YouTube”或发布到YouTube时使用此技能。
-
let x;:TDZ 从作用域入口持续到let x;这行执行完(此时x被初始化为undefined) -
const y = 10;:TDZ 从作用域入口持续到const y = 10;执行完(此时y被初始化为10) -
const z;是语法错误,根本无法通过解析,所以不涉及 TDZ —— 它连声明都失败
典型 TDZ 报错场景
以下代码都会触发 ReferenceError: Cannot access 'xxx' before initialization:
- 在
let/const声明前读取变量:console.log(a); // ReferenceError<br>let a = 1;
- 在声明前对变量进行 typeof(注意:
var下是"undefined",但let/const下仍报错):typeof b; // ReferenceError<br>let b;
- 函数内存在块级作用域,且在
let前访问:function foo() {<br> if (false) { let tmp; }<br> console.log(tmp); // ReferenceError —— TDZ 覆盖整个函数作用域<br>}
TDZ 与 var 提升的区别
var 会变量提升(hoisting),声明和初始化被拆开:声明被提升到作用域顶部,初始化(赋值)留在原地,未赋值时默认为 undefined;而 let/const 的声明和初始化是绑定的,且整个绑定过程受 TDZ 约束。
-
var c;→ 可以在声明前console.log(c),输出undefined -
let d;→ 在声明前访问,直接报ReferenceError,不给任何默认值
如何避免 TDZ 问题
- 养成“先声明、后使用”的习惯,尤其在块级作用域中
- 避免在声明语句上方写任何可能访问该变量的代码(包括
console.log、typeof、闭包捕获等) - 理解函数作用域和块作用域的 TDZ 范围:TDZ 是按「词法作用域」计算的,不是按执行顺序
- 工具辅助:ESLint 规则
no-use-before-define可捕获部分 TDZ 风险(但不能覆盖所有情况,如跨块访问)

















