登录
首页 >  文章 >  前端

JavaScript函数定义与调用方法

时间:2026-03-03 22:20:39 279浏览 收藏

本文深入剖析了JavaScript中普通函数与箭头函数在定义、调用及核心行为上的本质区别——普通函数拥有独立的this、作用域、arguments和prototype,支持new调用与上下文重绑定,适用于构造器、方法定义等需要动态执行环境的场景;而箭头函数则无自身this和arguments,继承外层词法作用域的this,不可new、不可重绑定,轻量简洁,专为回调、高阶函数等无需动态上下文的场合设计。掌握二者在this绑定时机、调用方式、构造能力及参数处理上的关键差异,能帮你精准避坑(如事件回调中this丢失、类中定时器绑定错误),写出更健壮、可维护的代码。

javascript函数如何定义与调用_什么是箭头函数与普通函数区别?

普通函数定义与调用:语法和执行上下文是关键

JavaScript 中用 function 关键字定义的函数,会创建独立作用域并绑定自己的 this 值。调用时行为取决于调用方式(直接调用、方法调用、call/apply 等)。

常见错误现象:this 指向意外丢失(比如作为回调传入 setTimeout 或事件监听器时);函数提升(hoisting)导致变量未初始化却可调用但返回 undefined

  • 定义后可立即调用:
    function greet(name) { return `Hello, ${name}`; }
    greet("Alice"); // "Hello, Alice"
  • 函数表达式需先赋值再调用:
    const sayHi = function(name) { return `Hi, ${name}`; };
    sayHi("Bob"); // "Hi, Bob"
  • 作为对象方法时,this 指向调用它的对象:
    const user = { name: "Charlie", getName() { return this.name; } };
    user.getName(); // "Charlie"

箭头函数定义与调用:没有自己的 thisarguments

箭头函数用 => 定义,不绑定 thisargumentssupernew.target,而是继承外层作用域的值。它不能用作构造函数(new 报错),也没有原型属性。

使用场景:适合简短回调、避免 this 绑定问题(如在 mapfilter 或事件处理中),但不适合需要动态 this 的方法定义。

  • 单参数可省括号,单表达式可省花括号和 return
    const add = (a, b) => a + b;
    add(2, 3); // 5
  • 对象字面量需加括号,否则被解析为代码块:
    const makeObj = () => ({ id: 1, name: "test" });
    makeObj(); // { id: 1, name: "test" }
  • 在类方法中用箭头函数保存实例 this
    class Counter {
      constructor() { this.count = 0; }
      start() {
        setInterval(() => { // 这里的 this 指向 Counter 实例
          this.count++;
          console.log(this.count);
        }, 1000);
      }
    }

this 行为差异:最常踩坑的地方

普通函数的 this 在调用时确定,而箭头函数的 this 在定义时就固定了——它永远等于外层非箭头函数作用域的 this

典型陷阱:把箭头函数写在对象方法内部,误以为它能访问对象自身属性;或在需要改变 this 的场景(如 bindcall)中强行使用箭头函数。

  • 普通函数可被重绑定:
    function logThis() { console.log(this); }
    logThis.call({ x: 42 }); // { x: 42 }
  • 箭头函数无视 call/apply/bind
    const arrow = () => console.log(this);
    arrow.call({ y: 99 }); // 仍输出外层 this(如全局对象或模块顶层 this)
  • 嵌套时箭头函数捕获的是最近一层普通函数的 this
    function outer() {
      console.log(this === window); // true(非严格模式)
      const inner = () => console.log(this === window); // 也是 true
      inner();
    }

不能 new、没有 prototype、不支持 arguments

箭头函数不是“可构造对象”,尝试 new 会抛出 TypeError: xxx is not a constructor。它没有 prototype 属性,也不能用 arguments 访问实参列表——必须用剩余参数 ...args 替代。

性能影响极小,但语义差异显著:如果你需要构造实例、动态 this、或兼容老代码中对 arguments 的依赖,就不能用箭头函数。

  • 箭头函数无 prototype
    const fn = () => {};
    console.log(fn.prototype); // undefined
  • 必须用剩余参数代替 arguments
    const sum = (...nums) => nums.reduce((a, b) => a + b, 0);
    sum(1, 2, 3); // 6
  • new 箭头函数直接报错:
    const Person = (name) => ({ name });
    new Person("Alice"); // TypeError: Person is not a constructor
普通函数和箭头函数的选择,本质上是“是否需要独立执行上下文”的判断。很多 bug 来自混淆两者对 thisnew 的处理逻辑,尤其在类、事件、定时器、高阶函数中。写之前先问一句:这个函数要不要被 new?要不要被别的 this 调用?要不要在不同上下文中复用?答案决定用哪个。

文中关于的知识介绍,希望对你的学习有所帮助!若是受益匪浅,那就动动鼠标收藏这篇《JavaScript函数定义与调用方法》文章吧,也可关注golang学习网公众号了解相关技术文章。

资料下载
相关阅读
更多>
最新阅读
更多>
课程推荐
更多>