无法在生成器内使用 'yield' 作为标识符

5

在编写一个异步生成器函数时,我注意到以下结构会导致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
}

但是这引出了一个问题,就是在这种情况下,yield被解析为标识符的具体静态语义是什么呢?而await则不需要特殊处理?涉及到的是ECMAScript 2018中哪些具体的静态语义。
1个回答

3
这是await操作符的优先级问题,它形成一个UnaryExpression(并将其作为操作数),而yield操作符形成一个AssignmentExpression(并将其作为可选操作数)。AssignmentExpression不形成UnaryExpression,这意味着您不能像那样嵌套它们。

解析await表达式时,下一个被解析的标记用于形成UnaryExpression,而yield唯一可以做到这一点的选择是作为IdentifierReference(完全忽略其后面的bar)。当然,在生成器解析上下文中是不允许的,导致了令人困惑的错误消息。

请注意,无论是嵌套形式的await (yield …)还是yield (await …)都是完全不必要的,因为异步生成器函数中的yield关键字已经在内部等待了产生的值和恢复的值internally,所以您应该省略await关键字,只使用yield

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接