【问题标题】:Iterator implementation in JSJS中的迭代器实现
【发布时间】:2018-10-06 07:27:04
【问题描述】:

我们可以让一个普通的 (POJSO) JS 对象可迭代,像这样:

const tempObj = {a: 1, b: 2, c: 3};

tempObj[Symbol.iterator] = function () {
  const self = this;
  const keys = Object.keys(self);
  return {
    next() {
      const k = keys.shift();
      return {
        done: !k,
        value: [k, self[k]]
      }
    }
  }
};

现在我们可以使用for..of循环:

for (let [k,v] of tempObj) {
  console.log(k,v);
}

我们得到:

a 1
b 2
c 3

我的问题是 - 除了 next() 之外,我们还需要实现另一种方法吗?如果不是,为什么迭代器规范选择返回一个对象而不是只返回一个函数?为什么规范不简单:

   tempObj[Symbol.iterator] = function () {
      return function next {
          return {
            done: Object.keys(this).length === 0,
            value: Object.keys(this).shift()
          }
      }
    };

我唯一的猜测是,通过返回一个对象,它为更新/更改留出了空间。

【问题讨论】:

标签: javascript node.js ecmascript-6 iterator


【解决方案1】:

您可以生成一个以 Object.entries 为值的生成器。

let tempObj = { a: 1, b: 2, c: 3 };

tempObj[Symbol.iterator] = function* () {
    yield* Object.entries(this);
};

for (let [k, v] of tempObj) {
    console.log(k, v);
}

【讨论】:

    【解决方案2】:

    Iterator 接口还支持另外两个可选方法:returnthrow。来自the ES6 specification,第 25.1.1.2 节(表 54):

    返回

    返回 IteratorResult 对象的函数。返回的 对象必须符合 IteratorResult 接口。调用这个 方法通知 Iterator 对象调用者不打算 对迭代器进行更多的 next 方法调用。返回的 IteratorResult 对象通常会有一个 done 属性,其值 为真,并且具有作为参数传递的值的值属性 返回方法。但是,此要求并未强制执行。

    投掷

    返回 IteratorResult 对象的函数。返回的对象 必须符合 IteratorResult 接口。调用此方法 通知 Iterator 对象调用者检测到错误 健康)状况。该参数可用于识别错误条件 并且通常是一个异常对象。一个典型的反应是 抛出作为参数传递的值。如果方法没有抛出, 返回的 IteratorResult 对象通常具有 done 属性 其值为真。

    ES6 规范还说:

    通常,这些方法的调用者应该在调用它们之前检查它们的存在。

    所以你绝对不需要实现它们;检查它们是否存在的负担由调用者承担。

    【讨论】:

      【解决方案3】:

      除了next()之外,我们还需要实现其他方法吗?

      不,没有我们需要实施,但我们可以实施throwreturn以获得完整的iterator interface .例如,生成器对象就是这样做的。

      为什么迭代器规范选择返回一个对象而不是仅仅返回一个函数?

      因为迭代器(通常)是有状态的,并且从 OOP 的角度来看,它应该是一个带有方法而不是(纯)函数的对象。这也允许迭代器实例的原型继承。

      【讨论】:

        猜你喜欢
        • 2021-11-16
        • 2020-11-09
        • 1970-01-01
        • 1970-01-01
        • 2023-02-03
        • 1970-01-01
        • 2016-01-23
        • 2012-01-22
        • 2018-03-14
        相关资源
        最近更新 更多