前端搜索(前端超细拆解第3期:前端函数与作用域链)

前端搜索(前端超细拆解第3期:前端函数与作用域链)
前端超细拆解第3期:前端函数与作用域链

函数是 JavaScript 的核心组成部分,作用域链则是 JS 实现变量查找、隔离的核心机制,二者共同决定了代码的执行逻辑和变量的可访问性。

(一)JavaScript 函数

函数是 “可重复执行的代码块”,也是 JS 中的一等公民(可作为参数、返回值、赋值给变量),核心包含函数声明、函数表达式、作用域、闭包等特性。

1. 函数的定义方式

| **函数表达式(Function Expression)** |// 匿名函数表达式const add = function(a, b) {  return a + b;};// 具名函数表达式const add = function fn(a, b) {  return a + b;};| 无变量提升(仅变量提升,函数体不提升);可匿名/具名;赋值后才能调用;具名表达式的函数名仅在函数内部可用。 || **箭头函数(Arrow Function)** |const add = (a, b) => a + b;// 多语句需加{}和returnconst sum = (a, b) => {  const res = a + b;  return res;};| 无`this`/`arguments`/`super`;不能作为构造函数(不能用`new`);语法简洁;继承外层作用域的`this`。 || **构造函数(不推荐)** | const add = new Function('a', 'b', 'return a + b'); | 性能差;作用域为全局;易导致安全问题,几乎不用。 |##### 2. 函数的核心特性- **参数**:  - 形参(定义时的参数)/实参(调用时的参数);  - 剩余参数(`...rest`):接收剩余所有实参,转为数组:    function sum(...nums) {      return nums.reduce((a, b) => a + b, 0);    }    sum(1,2,3); // 6
  • 参数默认值:function add(a = 0, b = 0) { return a + b; };
  • 返回值:无return则默认返回undefined;
  • this 指向(箭头函数无自身this):

调用方式

this 指向

前端搜索(前端超细拆解第3期:前端函数与作用域链)

普通函数直接调用

window(非严格模式)/undefined(严格模式)

对象方法调用

调用方法的对象

构造函数(new)

新创建的实例对象

call/apply/bind

指定的第一个参数

(二)作用域与作用域链

作用域(Scope)决定了变量 / 函数的可访问范围,作用域链则是 JS 查找变量的核心机制。

1. 作用域的分类

| **函数作用域** | 仅在函数内部可访问;函数执行完毕后销毁;变量提升仅在函数作用域内生效 |function fn() {  const localVar = '函数内变量'; // 函数作用域  console.log(localVar); // 可访问}console.log(localVar); // 报错:未定义| **块级作用域**(ES6+) | 由`{}`包裹(if/for/let/const);仅在块内可访问;`var`无块级作用域 |if (true) {  let blockVar = '块级变量'; // 块级作用域  var varVar = 'var变量'; // 无块级作用域,提升到外层}console.log(blockVar); // 报错console.log(varVar); // 可访问##### 2. 作用域链(Scope Chain)- **定义**:当访问一个变量时,JS引擎会先在当前作用域查找,若找不到则向上一级作用域查找,直到全局作用域,这个“查找链条”就是作用域链;- **形成原因**:函数创建时会记录当前的作用域环境(`[[Scope]]`属性),函数执行时会创建**执行上下文**,并将当前作用域与外层作用域连接成链;- **执行上下文**:函数执行时的环境,包含变量对象(VO)、作用域链、this指向,执行完毕后销毁(闭包除外)。##### 3. 核心示例(作用域链查找)const a = 1; // 全局作用域function fn1() {  const b = 2; // fn1作用域  function fn2() {    const c = 3; // fn2作用域    console.log(a + b + c); // 查找顺序:c(fn2)→ b(fn1)→ a(全局)→ 输出6  }  fn2();}fn1();

2. 闭包(作用域链的典型应用)

  • 定义:函数嵌套时,内层函数引用外层函数的变量,导致外层函数执行完毕后,其作用域不会被销毁,内层函数可继续访问该变量;
  • 示例
  • javascript
  • function outer() { let count = 0; // 内层函数引用outer的count,形成闭包 return function inner() { count++; console.log(count); }; } const fn = outer(); fn(); // 1 fn(); // 2(count未被销毁,持续累加)
  • 用途:私有化变量、缓存数据、实现模块化;
  • 注意:滥用闭包会导致内存泄漏(变量无法销毁),需及时释放(如fn = null)

文章版权声明:除非注明,否则均为边学边练网络文章,版权归原作者所有