前置知识
如果接触过 python 中迭代器和生成器,或者 Rxjs 中的观察者和迭代器模式,看到 JavaScript 中的 function* yield* 和迭代协议应该会会心一笑。
相关 AST spec
interface ForOfStatement <: ForInStatement {
type: "ForOfStatement";
await: boolean;
}
interface ForStatement <: Statement {
type: "ForStatement";
init: VariableDeclaration | Expression | null;
test: Expression | null;
update: Expression | null;
body: Statement;
}
用途
解析 for...of 语法
源码解析
源代码
代码比较长,这里就不整段贴了,gitee传送门
插件通过 option assumeArray 的值实现了两种 visitor,部分UT代码代码如下:
assumeArray == true通过js代码,实现ForOfStatement转为ForStatementassumeArray == false通过模板的方式实现转换
assumeArray == true
// input
for (const i of items) i;
// output
for (let _i = 0, _array = array; _i < _array.length; _i++) {
const elm = _array[_i];
console.log(elm);
}
assumeArray == false
// input
for (i of arr) {
}
// output
var _iterator = babelHelpers.createForOfIteratorHelper(arr),
_step;
try {
for (_iterator.s(); !(_step = _iterator.n()).done;) {
i = _step.value;
}
} catch (err) {
_iterator.e(err);
} finally {
_iterator.f();
}
有耐心的同学可以通过AST explorer生成AST语法树,结合Babel 插件开发手册,对比源码进行阅读。