为什么这个生成器会跳过 try 块之外的收益

Why does this generator skip a yield outside the try block?

本文关键字:try 收益 为什么      更新时间:2023-09-26

Background

我正在试验Generator.prototype.throw()的工作原理,并做了这个例子:

var myGen = function *() {
    try{
        yield 1;
        yield 2;
        yield 3;
        yield 4;
        yield 5;
    }
    catch(err) {
        console.log(err);
    }
    yield 7;
    yield 8;
    yield 9;
}
var myIterator = myGen();
console.log(myIterator.next());
console.log(myIterator.next());
console.log(myIterator.next());
myIterator.throw(new Error('Bullocks!'));
console.log(myIterator.next());
console.log(myIterator.next());
console.log(myIterator.next());

在运行时会导致以下结果:

{ value: 1, done: false }
{ value: 2, done: false }
{ value: 3, done: false }
[Error: Bullocks!]
{ value: 8, done: false }
{ value: 9, done: false }
{ value: undefined, done: true }

问题

我可以理解yield 4try块的剩余部分在抛出错误后被跳过。

但是为什么生成器会跳过yield 7

它不会跳过yield 7 . 调用 throw() 时,控制流进入catch块,记录错误,然后继续执行,直到返回新的迭代器结果对象{ value: 7, done: false }的下一个yield

只是在您的代码中,您不会console.log这个特定的结果对象。 尝试:

console.log(myIterator.throw(new Error('Bullocks!')));

规范的步骤 11 和 13 对此进行了解释:

  1. 使用 abruptCompletion恢复 genContext 的暂停评估,这是暂停它的操作的结果。让结果是恢复的计算返回的完成记录。
  2. (...
  3. 返回完成(结果)。