非常教程

Typescript参考手册

迭代器和发生器 | Iterators & Generators

Iterators & Generators

Iterables

如果对象具有Symbol.iterator属性的实现,则该对象被认为是可迭代的。一些内置的类型,如ArrayMapSetStringInt32ArrayUint32Array,等有自己的Symbol.iterator属性已经实施。Symbol.iterator函数对象负责返回要迭代的值列表。

for..of 声明

for..of循环遍历一个可迭代对象,调用该对象的Symbol.iterator属性。这是一个简单for..of的数组循环:

let someArray = [1, "string", false];

for (let entry of someArray) {
  console.log(entry); // 1, "string", false
}

for..offor..in声明

两者for..offor..in语句都遍历列表; 迭代的值虽然不同,但会for..in返回被迭代对象上的列表,而for..of返回正在迭代的对象的数值属性的列表。

下面是一个例子来证明这种区别:

let list = [4, 5, 6];

for (let i in list) {
   console.log(i); // "0", "1", "2",
}

for (let i of list) {
   console.log(i); // "4", "5", "6"
}

另一个区别在于for..in对任何物体进行操作; 它可以作为检查此对象属性的一种方法。for..of另一方面,主要关注可迭代对象的值。内置对象,MapSet实现Symbol.iterator允许访问存储值的属性。

let pets = new Set(["Cat", "Dog", "Hamster"]);
pets["species"] = "mammals";

for (let pet in pets) {
   console.log(pet); // "species"
}

for (let pet of pets) {
  console.log(pet); // "Cat", "Dog", "Hamster"
}

代码生成

针对ES5和ES3

在定位ES5或ES3时,迭代器只能用于Array类型的值。for..of在非数组值上使用循环是错误的,即使这些非数组值实现该Symbol.iterator属性。

编译器将为for循环生成一个简单的for..of循环,例如:

let numbers = [1, 2, 3];
for (let num of numbers) {
  console.log(num);
}

将生成为:

var numbers = [1, 2, 3];
for (var _i = 0; _i < numbers.length; _i++) {
  var num = numbers[_i];
  console.log(num);
}

定位ECMAScript 2015及更高版本

当定位符合ECMAScipt 2015的引擎时,编译器将生成for..of循环以定位引擎中的内置迭代器实现。

迭代器和发生器 | Iterators & Generators相关

Typescript

TypeScript 是 JavaScript 的类型的超集,它可以编译成纯 JavaScript。编译出来的 JavaScript 可以运行在任何浏览器上。

主页 https://www.typescriptlang.org
源码 https://github.com/Microsoft/TypeScript
发布版本 2.6.0