有人可以向我解释一下:为什么ES6中的生成器功能标有星号符号?
例如,而不是:
function *someGenerator() {
yield 1;
yield 2;
yield 3;
}
我们可以写:
function someGenerator() {
yield 1;
yield 2;
yield 3;
}
甚至:
var someGenerator = () => {
yield 1;
yield 2;
yield 3;
}
var someObject = {
someGenerator() {
yield 1;
yield 2;
yield 3;
}
}
JS编译器可以在解析时检测到someGenerator
包含yield
运算符,并使用此函数生成一个生成器。
为什么检测yield
存在不够?
答案 0 :(得分:55)
原因有三:
可读性。生成器与函数完全不同,差异应该立即可见(即,不检查整个实现以寻找收益)。
概论。自然可以编写不产生的生成器,并且只能直接返回。此外,评论身体的一部分(例如用于调试)不应该默默地改变某些东西是否是发电机。
兼容性。只保留严格模式' yield'作为关键字,但ES6的目标是所有新功能也以草率模式提供(不幸的决定恕我直言,但不过)。而且,即使在严格的模式下,也会有很多解析的细微差别在于' yield&#39 ;;例如,考虑默认参数:
function* g(a = yield(2)) { 'use strict' }
如果没有*
,解析器只能在看到函数体之后决定如何解析yield。也就是说,你需要无限的前瞻,或回溯,或其他hacky技术来解决这个问题。
我应该注意(1)和(2)已经足够了。
(完全披露:我是EcmaScript委员会的成员。)
答案 1 :(得分:7)
不允许空发电机(没有车身);那么unStarredFunc()
是否应遵循生成器语义?
出于兼容性原因:
function yield(x) { return x };
function a() {
yield (4+1);
};
这在语法上是正确的,但调用.next()
会导致错误,而添加星号以明确定义生成器会导致.next().value === 5
检测someGenerator在分析时包含yield运算符
在解析时无法解析某些构造:
function someGenerator(i) {
if (glob)
return 4;
else
yield* anotherGen(i);
}
当然,从function*
定义中直接看到它的生成器更简单,不需要深入研究其来源以寻找产量。