Generator.next()如何处理其参数?

Fed*_*ico 6 javascript ecmascript-6

该文件说:"你也可以提供一个参数下一个方法发送值到发电机上." 它将它发送到哪里?

例如,拿这三个发电机:

function* one() {
  while(true) {
    var value = yield null;
  }
}
var g1 = one();  g1.next();
g1.next(1000); //yields null

function* two() {
  var i = 0;
  while (true) {
    i += yield i;
  }
}
var g2 = two(); g2.next(); 
g2.next(1000) // yields 1000

function* three(){
  var index = 0;
  while (true)
    yield index++;
}

 g3 = three();
 g3.next();
 g3.next(1000); // yields 1
Run Code Online (Sandbox Code Playgroud)

在生成器3和1中,传递的参数对其没有影响next.这是为什么?发电机2如何计算其返回值?为什么它会受到给定参数的影响?

Fed*_*ico 14

理解这一点的关键是知道下一个函数如何检索传递给的参数next(),这是yield运算符的返回值:

[rv] = yield [expression];
Run Code Online (Sandbox Code Playgroud)

独立于[expression]的值,yield将赋值给rv传递给的值next().

但是,这里有一个棘手的部分:yield只会在从前一次迭代恢复执行时分配传递给next()的值.因此,在第一次迭代时,yields不会为rv分配任何内容.

例如,如果我有这个发电机:

function* gen() {
  // On the first iteration, yield does not return anything.
  //because it returns something ONLY when execution is resumed
  returnedFromYield = yield 'foo'; 
  yield returnedFromYield; 
}
Run Code Online (Sandbox Code Playgroud)

returnedFromYield在第一次迭代时未定义.当在第二次迭代时恢复执行时,yield将传递的值赋给returnedFromYield变量,然后返回该变量:

g.next(1); // 'foo'
g.next(2); // 2
Run Code Online (Sandbox Code Playgroud)

我们来看另一个例子:

function* gen() {
  yield yield yield 5;
}
Run Code Online (Sandbox Code Playgroud)

在第一次迭代时,(g.next()),yield将在第二次迭代时返回5,(g.next(10))yield将传递10到第二次yield.也就是说,yield yield yield 5;第二次迭代相当于yield yield 10;,并且,在第三次迭代中,它相当于yield valuePassedToNext.


小智 5

下面是一个带注释的示例,显示了传递给生成器的 next 方法的值的逻辑流程和范围。方法调用的受影响区域next以相应的颜色突出显示。

在此输入图像描述

a:没有产量,因此参数“one”被忽略。生成器在第 5 行暂停,返回值 1。

b:执行继续,“two”替换第 5 行的yield,并分配给yieldValue变量。第 6 行被执行。生成器在第 8 行暂停,返回值 2。

c:执行恢复,“三”替换第 8 行的yield,并分配给yieldValue变量。第 9 行被执行。生成器在第 11 行暂停,返回值 3。

d:执行恢复,“four”替换第 11 行的yield,并分配给变量yieldValue。第 12 行被执行。第 14 行被执行。最后,生成器现已完成,返回值undefined。

请参阅第 28-36 行日志