← 返回目录

第 10 卷

第 10 / 19 卷日期:

11fn2();

12const obj2 = { a: 20, fn: fn2 };

13obj2.fn();

• 输出结果:

1.10(箭头函数 arrowFn 继承 fn 的 this( obj),调用 fn2 时, this 仍指向 obj)

2.10(箭头函数 this 无法修改,即使作为 obj2 的方法调用,仍继承原上层作用域的 this)

面试题7:绑定优先级(new > bind > 隐式)

Code block

1function Person(a) { 2this.a = a;

3} 4const obj = { a: 10 };

5Person.prototype.fn = function() { 6console.log(this.a);

7};

8// bind绑定 9const PersonBind = Person.bind(obj);

10// new调用bind后的函数 11const p = new PersonBind(20);

12p.fn();

• 输出结果: 20( new 绑定优先级高于 bind, this 指向新实例 p, p.a=20,而非

obj)

19. 'var'、'let'和'const'用于变量声明,它们之间有何区别?请从作用

域、提升(hoisting)、以及是否允许重新赋值和重新声明的角度,详细比

较这三种声明方式。

var、 let、 const 是JavaScript中三种变量声明方式,核心区别集中在作用域、变量提升、重新赋值、重新声明四个维度,具体对比和说明如下:

(1)核心维度对比表

变量提升存在(提升到作用域顶部,初存在(提升到块级作用域顶存在(同let,提升
始值为undefined)部,但未初始化,处于暂时性化,暂时性死区)

死区)

重新赋值允许允许不允许(常量,赋改)

重新声明允许(同一作用域内可重复声不允许(同一作用域内不可重不允许(同一作用
明)复声明)复声明)
初始赋值可选(声明后可后续赋值)可选(声明后可后续赋值)必须(声明时必须

报错)

全局变量挂载挂载到全局对象不挂载到全局对象(仅全局作不挂载到全局对象(window/global)用域可见,不污染全局对象)

(2)逐维度详细说明

  1. 作用域差异

• var:仅支持函数作用域和全局作用域,无块级作用域。这意味着 var 声明的变量会穿透 if、

for、 {} 等块级结构,在块外部仍可访问。

Code block

1if (true) { 2var a = 10; // var无块级作用域

3} 4console.log(a); // 10(穿透if块,外部可访问)

5 6for (var i = 0; i < 3; i++) {

7// var声明的i无块级作用域 8}

9console.log(i); // 3(穿透for块,外部可访问)

• let/const:支持块级作用域、函数作用域和全局作用域。变量仅在其声明的 {} 块内可访问,块外

部无法访问,解决了 var 的变量穿透问题。

Code block

1if (true) {

8for (let i = 0; i < 3; i++) {

9// let声明的i有块级作用域,每次循环创建独立i
10}
11console.log(i);//报错:ReferenceError: i is not defined
  1. 变量提升差异

• var:存在完整的变量提升。 var 声明的变量会被提升到其作用域的顶部,且初始值被设置为

undefined,因此在声明前访问变量不会报错,仅返回 undefined。

Code block

1console.log(a); // undefined(var变量提升,初始值为undefined)

2var a = 10;

  • let/const:存在“不完全变量提升”(也叫“提升但未初始化”)。
  1. 本质: let/const 声明的变量会被提升到其块级作用域的顶部,但引擎不会为其分配初始值(未

初始化状态);

  1. 暂时性死区(TDZ):从块级作用域开始到变量声明完成之前,该变量处于“暂时性死区”,在此

期间访问变量会直接报错,而非返回 undefined;

  1. 与 var 的区别: var 提升后初始化为 undefined, let/const 提升后未初始化,存在

TDZ,更安全。

Code block

1console.log(b); // 报错:ReferenceError: Cannot access 'b' before initialization (TDZ)

2let b = 20;

3 4console.log(c); // 报错:ReferenceError: Cannot access 'c' before initialization

(TDZ)

5const c = 30;

  1. 重新赋值差异
  • var:允许重新赋值。声明后的变量可以多次修改其值。
全站分卷索引 · 19 卷
  1. 1第 1 卷
  2. 2第 2 卷
  3. 3第 3 卷
  4. 4第 4 卷
  5. 5第 5 卷
  6. 6第 6 卷
  7. 7第 7 卷
  8. 8第 8 卷
  9. 9第 9 卷
  10. 10第 10 卷
  11. 11第 11 卷
  12. 12第 12 卷
  13. 13第 13 卷
  14. 14第 14 卷
  15. 15第 15 卷
  16. 16第 16 卷
  17. 17第 17 卷
  18. 18第 18 卷
  19. 19第 19 卷