3

在编写异步生成器函数时,我注意到以下构造导致 a SyntaxError

async function * foo() {
  await yield bar; // Can not use 'yield' as identifier inside a generator
}

即使颠倒上下文关键字的顺序是完全可以接受的:

async function * foo() {
  yield await bar; // OK
}

UnaryExpression仔细阅读错误后,我能够通过将括号括在括号内来更正语法,AwaitExpression以避免将令牌解析yield为标识符而不是上下文关键字:

async function * foo() {
  await (yield bar); // OK
}

但这引出了一个问题,ECMAScript 2018中涉及哪些特定的静态语义导致yield在这种情况下被解析为标识符,await而不需要特殊处理?

4

1 回答 1

2

这是运算符的优先级问题await,它形成 aUnaryExpression(并有一个作为其操作数),与形成 anyield的运算符不同(并有一个作为其可选操作数)。An不形成 a ,这意味着您根本不允许像那样嵌套它们。AssignmentExpressionAssignmentExpressionUnaryExpression

解析表达式时await,输入解析的下一个标记用于形成 a UnaryExpression,并且这样做的唯一选择yield是作为 a IdentifierReference(完全忽略bar它后面的)。当然,在不允许的生成器解析上下文中,会导致令人困惑的错误消息。

请注意,两种形式的嵌套 (await (yield …)yield (await …)) 无论如何都是完全没有必要的,因为异步生成器函数中的关键字已经在内部yield等待产生值和恢复值,因此您应该省略关键字并仅使用。awaityield

于 2019-12-10T18:56:39.300 回答