JS中的箭頭函數和普通函數有什么區別?

箭頭函數與普通函數的關鍵區別在于this綁定、構造函數能力和arguments對象。1. this指向不同:普通函數的this取決于調用方式,而箭頭函數繼承外層作用域的this,如在對象方法中使用可能無法訪問對象屬性;2. 箭頭函數不能作為構造函數,無法通過new創建實例;3. 箭頭函數無自己的arguments對象,引用外層函數的arguments,建議改用rest參數替代;適合在無需改變this、非構造函數、不依賴arguments的場景使用,反之則應避免。

JS中的箭頭函數和普通函數有什么區別?

箭頭函數和普通函數在JavaScript中有一些關鍵區別,主要體現在this的綁定方式、作為構造函數的能力、以及是否有自己的arguments對象這幾個方面。


1. this的指向不同

這是最常被提到也是最重要的區別之一。

  • 普通函數有自己的this上下文,它的值取決于函數被調用的方式。
  • 箭頭函數沒有自己的this,它會繼承外層作用域中的this值。

舉個例子:

const obj = {   name: 'Tom',   sayNameNormal: function() {     console.log(this.name);   },   sayNameArrow: () => {     console.log(this.name);   } };  obj.sayNameNormal(); // 輸出 "Tom" obj.sayNameArrow();  // 輸出 undefined(或外層作用域的 this)

如果你在一個對象的方法里使用箭頭函數,并希望訪問該對象的屬性,那就得小心了,因為this可能不是你預期的對象。


2. 箭頭函數不能作為構造函數

構造函數是用來通過new關鍵字創建對象的。普通函數可以這么做,但箭頭函數不行。

function Person(name) {   this.name = name; }  const p = new Person('Alice'); // 正常創建對象  const Animal = (name) => {   this.name = name; };  const a = new Animal('Dog'); // 報錯:Animal is not a constructor

所以如果你想定義一個類或者工廠函數來生成實例,就不能用箭頭函數。


3. 箭頭函數沒有自己的arguments對象

普通函數可以通過arguments來訪問傳入的所有參數,而箭頭函數中使用arguments會引用外層函數的arguments,這可能導致意料之外的行為。

function foo() {   const bar = () => {     console.log(arguments); // 拿的是 foo 的 arguments   };   bar(); }  foo(1, 2, 3); // 輸出 [Arguments] { '0': 1, '1': 2, '2': 3 }

如果想避免這種行為,建議使用es6的rest參數替代:

const bar = (...args) => {   console.log(args); };

4. 哪些時候適合用箭頭函數?

  • 在不需要改變this指向的地方,比如數組的.map()、.Filter()等方法內部
  • 寫簡潔的一行函數時
  • 不需要作為構造函數的時候

什么時候應該避免使用箭頭函數?

  • 當你需要一個構造函數時
  • 在對象的方法中,如果需要用到this
  • 如果你依賴arguments對象(雖然現在有更好的替代方案)

基本上就這些區別。理解它們的關鍵點在于:箭頭函數更輕便,但在某些場景下并不適用。

? 版權聲明
THE END
喜歡就支持一下吧
點贊14 分享