为什么我们使用 [Symbol.iterator] 而不是 `for` 循环?

Why do we use [Symbol.iterator] instead of a `for` loop?

我正在阅读 Eloquent JavaScript's "The Iterator Interface" section and I have trouble understanding why we need to define MatrixIterator function to iterate Matrix's contents. I usually use for inside of another for to iterate the contents of a two-dimensional matrix, similar to this。是不是因为当你调用for循环的shorthand时,JS中每个对象的[Symbol.iterator]都会被使用for...of

此外,我是否正确假设标准 [Symbol.iterator] 不能自动迭代二维对象,因此需要创建 MatrixIterator 并将其分配为:

Matrix.prototype[Symbol.iterator] = function() {
  return new MatrixIterator(this);
};

我们可以这样做吗:Matrix.prototype[Symbol.iterator] = MatrixIterator;?

题外话:我觉得我应该更深入地了解一些其他的东西,因为我对这些概念感到很困惑。有人还可以详细说明接口的含义吗?书中确实提到了它:

Different pieces of such a program interact with each other through interfaces, limited sets of functions or bindings that provide useful functionality at a more abstract level, hiding their precise implementation.

Separating interface from implementation is a great idea. It is usually called encapsulation.

但它没有提到实现是什么。

the shorthand of for loop which is for...of?

不,for … of 不是正常 for (…; …; …) 循环的 shorthand。这是一个完全独立的机制。

Why do we need to define MatrixIterator function to iterate Matrix's contents?. Is it because the [Symbol.iterator]'s of each object in JS is used whenever you use for...of?

是的。我们定义 MatrixIterator 是因为它符合迭代器接口,正如预期由 Symbol.iterator 方法返回以在这样的循环中可用。

当然还有其他方法可以实现,我们不一定需要额外制作MatrixIterator class。生成器函数通常是最简单的。

I usually use for inside of another for to iterate the contents of a two-dimensional matrix

当然可以,但这是相当多的语法开销 - 两个循环、两个计数器、双缩进。它可能会简单得多,并且当我们想要迭代矩阵时,我们不想在任何地方重复这种模式。可迭代接口允许这样做。

am I correct to assume that the standard [Symbol.iterator] cannot automatically iterate a two-dimensional objects

没有标准的Symbol.iterator方法。每种类型都需要自己定义。例如,Array.prototype 可以,但它只适用于数组,不适用于我们的 Matrix class.

Are we allowed to do this instead: Matrix.prototype[Symbol.iterator] = MatrixIterator;?

那是行不通的,因为 MatrixIterator a) 是一个需要用 new 调用的构造函数 b) 将它应该迭代的矩阵实例作为参数