【问题标题】:Do we need to wrap ES6 code in an IIFE?我们是否需要将 ES6 代码包装在 IIFE 中?
【发布时间】:2016-09-20 19:46:52
【问题描述】:

在 ES5 中,编写这样的代码被认为是一种好的做法:

(function () {
    //some magic
})();

但在 ES6 中使用 let 关键字创建的变量不会附加到 window 对象。

那么,现在有没有必要在 IIFE 中编写我们的代码,或者它还有一些我没有听说过的用途?

【问题讨论】:

  • "使用 let 关键字创建的变量未附加到 window 对象" - 但它们仍然是全局的。因此,如果您正在编写脚本,则需要将它们放在一个块或 IIFE 中。
  • @Bergi 这个问题不是您链接的问题的副本吗?
  • @Gothdo:也许吧,但我不确定对 const+let 的关注是否确实让它们有所不同,所以我不想欺骗锤子。随意投下你的一票;如果 OP 同意,我会很乐意关闭。

标签: javascript ecmascript-6 encapsulation iife


【解决方案1】:

如果您使用模块,则无需使用 IIFE(这就是调用此“包装器”的方式),因为所有变量的范围都仅限于模块。

但是,在某些情况下,您仍然希望将代码的一部分与另一部分分开,然后您可以使用 IIFE。

当然,如果您使用letconst,您可以使用块语句代替IIFE:

{
  let something = 1;
  const somethingElse = 2;
}
console.log(something); // ReferenceError: something is not defined

查看 Programmers.SE 上的相关问题:How far should encapsulation in JavaScript go?

【讨论】:

  • 据我了解,ES6 类本质上提供了与 IIFE 相同或接近相同的功能。对吗?
  • @lux 不,ES6 类不同。
  • this 是封装在类里的吧?
  • @lux 这个问题与课程无关。如果您想讨论这个问题,请提出另一个问题或在chat 中问我。
  • @lux:不,类什么都不封装。它们与带有方法定义的对象字面量一样好。
【解决方案2】:

现在问题不那么严重了,但我认为这个总体思路还是有原因的。

理论上,某些第三方库可以编写如下代码:

let count = 0;
function getCount() {
  return count++;
}

现在,如果您尝试在同一范围内创建自己的 count 变量,则会收到错误消息:

// 3rd-party
let count = 0;
function getCount() {
  return count++;
}

// Your code
let count = 1;

但是,您可以通过使用实际块而不是 IIFE 来使代码更简洁。

// Still bad 3rd party
let count = 0;
function getCount() {
  return count++;
}

// Your code
{
  let count = 10;
  console.log(count);
  console.log(getCount());
  console.log(count);
  console.log(getCount());
}

将来,您应该能够将代码封装在具有自己作用域的模块中,而无需将代码包装在 IIFE 或块中。

【讨论】:

  • ES6 类中的词法作用域如何影响这一点?
  • @lux 与上一个示例中的相同。在不同范围内声明的任何变量(包括类中的方法)都将隐藏外部范围内的变量,而不会尝试重新定义原始变量。同样,如果您尝试在一个范围内声明一个名为 X 的类,而该范围内已经有另一个名为 X 的类或任何其他变量,那么您将遇到重新定义错误。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-09-17
  • 1970-01-01
  • 1970-01-01
  • 2021-01-06
  • 2014-05-04
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多