迭代器模式是一种行为设计模式,它允许你在不暴露对象底层表示的情况下遍历对象的元素。迭代器模式通过提供一个迭代器来访问容器中的元素,使得容器可以提供多种遍历方式,同时可以隐藏容器内部的数据结构细节。
通常来说,迭代器模式包含两个主要的对象:迭代器和可迭代对象。可迭代对象是一个对象,它知道如何创建迭代器并且可以迭代它自己的元素。迭代器是一个对象,它知道如何遍历一个可迭代对象并且追踪当前遍历的位置。
迭代器模式可以在不改变可迭代对象代码的情况下,为其提供多种不同的遍历方式。此外,由于迭代器独立于容器,所以容器的结构可以更改而不会影响到遍历。迭代器模式还可以提供更简洁的遍历接口,因为它允许你使用通用的遍历方法来遍历不同类型的容器。
TypeScript 实现
在 TypeScript 中实现迭代器模式,可以定义一个接口 Iterator,它描述了迭代器应该实现的方法:
interface Iterator<T> {
next(): {
value: T;
done: boolean;
};
}
然后,我们可以使用该接口来定义一个集合的抽象类 Aggregate,其中包含一个方法 createIterator,它应该返回一个实现 Iterator 接口的迭代器对象:
abstract class Aggregate<T> {
protected data: T[];
constructor(data: T[]) {
this.data = data;
}
public abstract createIterator(): Iterator<T>;
}
接下来,我们可以定义一个具体的迭代器对象 ArrayIterator,它实现了 Iterator 接口,并可以遍历一个数组:
class ArrayIterator<T> implements Iterator<T> {
private index: number = 0;
constructor(private data: T[]) {}
public next() {
if (this.index >= this.data.length) {
return {
value: null,
done: true,
};
} else {
return {
value: this.data[this.index++],
done: false,
};
}
}
}
最后,我们可以定义一个具体的集合对象 ArrayAggregate,它继承了 Aggregate 抽象类,实现了 createIterator 方法,返回一个 ArrayIterator 迭代器对象:
class ArrayAggregate<T> extends Aggregate<T> {
constructor(data: T[]) {
super(data);
}
public createIterator(): Iterator<T> {
return new ArrayIterator<T>(this.data);
}
}
使用迭代器模式可以让集合对象和遍历算法解耦,提高代码的可维护性和可扩展性。
JavaScript 实现
在 JavaScript 中实现迭代器模式可以通过 Symbol.iterator 和 Generator 函数来实现。
Symbol.iterator 是一个内置的 Symbol 类型属性,它定义了对象的默认迭代器。在 ES6 中,所有的内置迭代器都是使用 Symbol.iterator 实现的。
Generator 函数是 ES6 中引入的一种新的函数类型,它通过 yield 语句实现了函数的暂停和恢复。
下面是一个使用 Generator 函数实现迭代器模式的示例:
function* createIterator(items) {
for (let i = 0; i < items.length; i++) {
yield items[i];
}
}
const iterator = createIterator([1, 2, 3]);
console.log(iterator.next()); // { value: 1, done: false }
console.log(iterator.next()); // { value: 2, done: false }
console.log(iterator.next()); // { value: 3, done: false }
console.log(iterator.next()); // { value: undefined, done: true }