如何解决在使用 Babel 转换箭头函数时发生的问题

如果你已经接触过 ES6 及以上的版本,那么你一定会使用过箭头函数。然而,受限于一些老旧的浏览器和版本,箭头函数并不能在所有场景下正常地运行。同时,如果使用了 Babel 转换器来将代码翻译成更低版本的 JavaScript,你也可能遇到一些问题。在本篇文章中,我们将会讨论如何解决在使用 Babel 转换箭头函数时发生的问题。

什么是 Babel?

首先,我们需要了解什么是 Babel。Babel 是一个广泛使用的 JavaScript 语法翻译器,它可以将 ES6+ 的代码,转化成向下兼容的 JavaScript 版本,使得我们可以在更广泛的浏览器和环境下使用这些特性。

Babel 的工作流程如下:

  1. 将代码解析成 AST(抽象语法树)
  2. 将 AST 转化成新的 AST (新的 AST 为 Babel 特有的格式)
  3. 将新的 AST 转化成代码

为什么会有问题?

然而,在转换箭头函数时,我们可能会遇到以下问题:

----- ------ - -
  ----- --------
  -------- -
    ---------
    ----------
    ------------
  --
  ----------- -- -- -
    --------------------- - - ----- - - -------------------- ----
  -
-

--------------------

运行结果如下:

--------- ----- ------- -------- ----------

我们本意是想要输出 Alice likes coding, reading, travelling,但实际上输出的却是 undefined likes coding, reading, travelling。这是因为箭头函数的 this 始终指向它所在上下文中的 this 对象,而不是函数自身的 this。由于我们在上述代码中没有显式绑定 this,所以 console.log 语句中的 this.namethis.hobbies 实际上都指向了 window 对象,因此 undefined 这个值就冒出来了。

在这种情况下,如果我们使用 Babel 将代码转换成 ES5 版本的代码,上述代码的结果将会是完全一样的:

----- ------ - -
  ----- --------
  -------- -
    ---------
    ----------
    ------------
  --
  ----------- -------- ------------ -
    --------------------- - - ----- - - -------------------- ----
  -
--

--------------------

运行结果同样为:

--------- ----- ------- -------- ----------

这并不是我们想要的效果。因此,我们需要使用一些方法来解决这个问题。

解决方法

我们可以使用两种方法来解决这个问题。

切换至普通函数

首先,我们可以将箭头函数换成普通函数。这是最简单的方法,但它也可能会带来额外的问题:

----- ------ - -
  ----- --------
  -------- -
    ---------
    ----------
    ------------
  --
  ----------- ---------- -
    --------------------- - - ----- - - -------------------- ----
  -
--

--------------------

运行结果为:

----- ----- ------- -------- ----------

这种方法可能会受限于一些情况,例如当我们需要在函数内部访问外部变量时,或者当我们需要在保留 this 的同时使用 => 符号时。因此,这种方法并不是总能适用。

使用 bind() 绑定 this

第二种方法是使用 bind() 来绑定 thisbind() 方法将会返回一个新的函数,同时将原本函数中的 this 指向传递进来的参数。这种方法的优势在于它能够在保留箭头函数的同时正确地绑定 this

----- ------ - -
  ----- --------
  -------- -
    ---------
    ----------
    ------------
  --
  ----------- ---------- -
    --------------------- - - ----- - - -------------------- ----
  --
  ---------------- ---------- -
    ------ ---------------------- -- ------------- ----- -----------
  --
  --------------- ---------- -
    ------ -------------------------------- -
      ------ ------------- ----- ---------
    --------------
  -
--

-------------------- -- ----- ----- ------- -------- ----------
-------------------------------------- -- - ---------- ----- -------- ---------- ----- --------- ---------- ----- ----------- -
------------------------------------- -- - ------ ----- -------- ------ ----- --------- ------ ----- ----------- -

上述代码中,我们为 person 对象增加了两个方法,分别是 getHobbiesArrow()getHobbiesBind()。在 getHobbiesArrow() 方法中,我们使用了箭头函数求值。在 getHobbiesBind() 方法中,我们将函数用 bind() 方法绑定了 this。运行结果显示,两种方法得到了不同的输出。

如果你需要对箭头函数使用绑定 this 的方法,可以将箭头函数放在一个常规函数中,然后再将常规函数绑定 this。例如:

----- ------ - -
  ----- --------
  -------- -
    ---------
    ----------
    ------------
  --
  ----------- ---------- -
    --------------------- - - ----- - - -------------------- ----
  --
  -------------------- ---------- -
    ------ --------------------------------- -
      ------ -- -- ------------- ----- ----------
    ---------------
  -
--

----------------------------------------------- -- -------

运行结果为:

- ------ ----- -------- ------ ----- --------- ------ ----- ----------- -

在这个例子中,我们使用了糟糕的代码把箭头函数解构到一个常规函数中,然后再将常规函数绑定到 this。虽然这不是最好的方案,但它可以让我们在箭头函数中继续使用 this,并且在转换至 ES5 时不会出现问题。

结论

在使用 Babel 转换器时,箭头函数可能会出现绑定问题。我们可以通过将箭头函数替换成普通函数,或者将函数用 bind() 方法绑定来解决问题。虽然这些方法并不总是完美的,但它们可以帮助我们继续使用箭头函数,并且立即享受它们的简洁性和清晰性。

通过本文,您已经学会了如何解决在使用 Babel 转换箭头函数时发生的问题,相信这对于您的前端开发工作会有很大帮助。

来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/6737218c317fbffedf084cf6