定义
可迭代对象,必须实现[Symbol.iterator]()方法(要么该对象有这个属性,要么它的原型链上有这个属性)
当一个对象需要被迭代时(比如在一个 for...of 循环中),首先会不带参数调用它的 [Symbol.iterator](),然后使用此方法返回的迭代器获取迭代的值
迭代器是一个拥有 next 方法的对象,返回符合 IteratorResult 接口的对象(包含 value、done 等属性)
内置的可迭代对象
- String
- Array
- Map
- Set
// String
const text = "Hello";
for (const char of text) {
console.log(char);
}
// Array
const numbers = [1, 2, 3];
for (const number of numbers) {
console.log(number);
}
// Map
const map = new Map([
["key1", "value1"],
["key2", "value2"],
]);
for (const [key, value] of map) {
console.log(`${key}: ${value}`);
}
// Set
const set = new Set([1, 2, 3, 4, 5]);
for (const value of set) {
console.log(value);
}
接受可迭代对象的 API
- Map()
- WeakMap()
- Set()
- WeakSet()
- Promise.all()
- Promise.allSettled()
- Promise.race()
- Promise.any()
- Array.from()
// Map()
const entries = [
["key1", "value1"],
["key2", "value2"],
];
const map = new Map(entries);
console.log(map.get("key1")); // 输出: value1
// WeakMap()
const key = { name: "WeakMapKey" };
const weakMap = new WeakMap([[key, "value"]]);
console.log(weakMap.get(key)); // 输出: value
// Set()
const items = [1, 2, 3, 3];
const set = new Set(items);
console.log(set.size); // 输出: 3
// WeakSet()
const key1 = { name: "WeakSetKey1" };
const key2 = { name: "WeakSetKey2" };
const weakSet = new WeakSet([key1, key2]);
console.log(weakSet.has(key1)); // true
// Promise.all()
Promise.all([Promise.resolve(1), Promise.resolve(2)]).then((values) =>
console.log(values)
); // 输出: [1, 2]
// Promise.allSettled()
Promise.allSettled([Promise.resolve(1), Promise.reject(2)]).then((results) =>
console.log(results)
);
// 输出: [{status: "fulfilled", value: 1}, {status: "rejected", reason: 2}]
// Promise.race()
Promise.race([
Promise.resolve("First"),
new Promise((resolve) => setTimeout(() => resolve("Second"), 1000)),
]).then((value) => console.log(value)); // 输出: First
// Promise.any()
Promise.any([Promise.reject("First"), Promise.resolve("Second")]).then(
(value) => console.log(value)
); // 输出: Second
// Array.from()
const map = new Map([
[1, "one"],
[2, "two"],
]);
const array = Array.from(map);
console.log(array); // 输出: [[1, 'one'], [2, 'two']]
一些期望可迭代对象的语句和表达式
- for...of 循环
- 数组和参数的扩展
- yield*
- 数组解构
// for...of
const iterableArray = [1, 2, 3, 4];
for (const value of iterableArray) {
console.log(value);
}
// 输出:
// 1
// 2
// 3
// 4
// 扩展
function sum(x, y, z) {
return x + y + z;
}
const numbers = [1, 2, 3];
const result = sum(...numbers); // 相当于调用 sum(1, 2, 3)
console.log(result); // 输出: 6
// yield
function* generatorOne() {
yield 1;
yield 2;
yield* [3, 4, 5]; // 委派给数组
yield 6;
}
const genOne = generatorOne();
console.log(genOne.next().value); // 1
console.log(genOne.next().value); // 2
console.log(genOne.next().value); // 3
console.log(genOne.next().value); // 4
console.log(genOne.next().value); // 5
console.log(genOne.next().value); // 6
// 解构
const [a, b, ...rest] = [1, 2, 3, 4, 5];
console.log(a); // 1
console.log(b); // 2
console.log(rest); // [3, 4, 5]
示例
string 的 [Symbol.iterator] 方法
const someString = "Hello World";
const iterator = someString[Symbol.iterator]();
console.log(iterator.next()); // { value: 'H', done: false }
console.log(iterator.next()); // { value: 'e', done: false }
console.log(iterator.next()); // { value: 'l', done: false }
自定义可迭代对象
const myIterable = {
*[Symbol.iterator]() {
yield 1;
yield 2;
yield 3;
},
};
console.log([...myIterable]); // [1, 2, 3]