javascript - 为什么 CoffeeScript 会编译为不惯用的 JavaScript?

标签 javascript coffeescript

我正在玩 CoffeeScript (我是这种“语言”的新手)并尝试了一个非常基本的示例:

x = [1, 2, 3] 
for element in x 
  console.log(element)

这正如它所说的那样,对于将其输出到控制台的每个元素。只是当我仔细研究了它编译的 Javascript 后,我​​才无法理解他们为什么这样做:

(function() {
  var element, i, len, x;

  x = [1, 2, 3];

  for (i = 0, len = x.length; i < len; i++) {
    element = x[i];
    console.log(x[i]);
  }

}).call(this);

这样做是否会更好并且更自然:

for(i = 0; i < x.length; i++)
{
   console.log(x[i]);
}

为什么 CoffeeScript 编译成这样看起来不自然的方式?如果我在 Javascript 中编写相同的代码,我会遵循我所做的方法,但我可能会错,因为我这样做的方式(Javascript)不是最有效或“自然”的,而 CoffeeScript 方法是更好的解决方案。

最佳答案

基本上,您期望 CoffeeScript 编译器执行非常复杂的操作。

考虑这个 CoffeeScript:

for a in x
  console.log(a)
  for b in a
    console.log(b)
    callFunc(b)

这会转换为:

for (i = 0, len = x.length; i < len; i++) {
  a = x[i];
  console.log(a);
  for (j = 0, len1 = a.length; j < len1; j++) {
    b = a[j];
    console.log(b);
    callFunc(b);
  }
}

很容易看出原始 CoffeeScript 如何与生成的 JavaScript 相对应:

for [variable] in [array]
    [body]

变成了

for (var [letter] = 0, len = [array].length, [letter] < len; [letter]++) {
    [variable] = [array][[letter]]
    [body converted to JavaScript]
}

因此,当将 for 理解式翻译成 JavaScript 时,(几乎)编译器需要担心的就是这个简单的对应关系,然后它可以向内工作并将主体作为单独且独立的操作进行处理.

此外,len = [array].length 缓存也是为了提高性能。这看起来并不完全令人愉快,而且大多数人不会以这种方式编码,但生成漂亮的 JavaScript 并不是 CoffeeScript 的主要目标。它生成高效的代码,假设人们通常不会阅读生成的 JavaScript。

您的建议是采用原始代码并将其转换为:

for (i = 0; i < x.length; i++) {
  console.log(x[i]);
  for (j = 0; j < x[i].length; j++) {
    console.log(x[i][j]);
    callFunc(x[i][j]);
  }
}

为了将 console.log(b) 转换为 console.log(b);,编译器不需要知道任何事情 关于该语句周围的代码。为了将 console.log(b) 转换为 console.log(x[i][j]);,编译器必须采用所有内容 围绕该声明考虑在内。它会给编译器带来极其复杂的工作,并且不会真正提供任何好处。

关于javascript - 为什么 CoffeeScript 会编译为不惯用的 JavaScript?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28742969/

相关文章:

javascript - 使用 CoffeeScript 进行缓存的问题

javascript - 我可以在 Angular 模块中同时使用两个分析插件吗?

coffeescript - 我可以使用 CoffeeScript 来编写我的 Electron (Atom Shell) 应用程序吗?

node.js - 引用错误: t is not defined

javascript - 使用 JavaScript 对 Web 应用程序进行 Android 浏览器震动检测

ruby-on-rails - rails 4 + ReactJS : "SyntaxError: cannot have an implicit value in an implicit object"

javascript - Rails - 使用 ajax 隐藏输入字段使用/传递参数

javascript - 如何处理 AMP 的 CORS

javascript - 在没有 ARRAY 的 Node JS 中循环 JSON

javascript - 弹出窗口在 asp.net 和 vb.net 网页上不起作用