Iterator
Baseline
Weitgehend verfügbar
*
Diese Funktion ist gut etabliert und funktioniert auf vielen Geräten und in vielen Browserversionen. Sie ist seit September 2016 browserübergreifend verfügbar.
* Einige Teile dieser Funktion werden möglicherweise unterschiedlich gut unterstützt.
Ein Iterator-Objekt ist ein Objekt, das dem Iterator-Protokoll entspricht, indem es eine next()-Methode bereitstellt, die ein Iterator-Ergebnisobjekt zurückgibt. Alle integrierten Iteratoren erben von der Klasse Iterator. Die Klasse Iterator stellt eine [Symbol.iterator]()-Methode bereit, die das Iterator-Objekt selbst zurückgibt, wodurch der Iterator auch iterierbar wird. Sie stellt außerdem einige Hilfsmethoden für die Arbeit mit Iteratoren bereit.
Beschreibung
Die folgenden sind allesamt integrierte JavaScript-Iteratoren:
- Der Array Iterator, der von
Array.prototype.values(),Array.prototype.keys(),Array.prototype.entries(),Array.prototype[Symbol.iterator](),TypedArray.prototype.values(),TypedArray.prototype.keys(),TypedArray.prototype.entries(),TypedArray.prototype[Symbol.iterator]()undarguments[Symbol.iterator]()zurückgegeben wird. - Der String Iterator, der von
String.prototype[Symbol.iterator]()zurückgegeben wird. - Der Map Iterator, der von
Map.prototype.values(),Map.prototype.keys(),Map.prototype.entries()undMap.prototype[Symbol.iterator]()zurückgegeben wird. - Der Set Iterator, der von
Set.prototype.values(),Set.prototype.keys(),Set.prototype.entries()undSet.prototype[Symbol.iterator]()zurückgegeben wird. - Der RegExp String Iterator, der von
RegExp.prototype[Symbol.matchAll]()undString.prototype.matchAll()zurückgegeben wird. - Das von Generatorfunktionen zurückgegebene
Generator-Objekt. - Der Segments Iterator, der von der
[Symbol.iterator]()-Methode desSegments-Objekts zurückgegeben wird, das vonIntl.Segmenter.prototype.segment()zurückgegeben wird. - Der Iterator Helper, der von Iterator-Hilfsmethoden wie
Iterator.prototype.filter()undIterator.prototype.map()zurückgegeben wird.
Web-APIs können ebenfalls Iteratoren zurückgeben. Einige verwenden JavaScript-Kerniteratoren wieder, während andere eigene Iteratoren definieren. Zum Beispiel:
- Array-ähnliche Objekte wie
NodeListgeben über ihre jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()einen Array Iterator zurück. - Map-ähnliche Objekte aus Web-APIs wie
Headersgeben über ihre jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()einen eigenen Iteratortyp wie Headers Iterator zurück. - Set-ähnliche Objekte aus Web-APIs wie
FontFaceSetgeben über ihre jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()einen eigenen Iteratortyp wie FontFaceSet Iterator zurück.
Hinweis:
NodeIterator und andere alte Schnittstellen tragen zwar diesen Namen, entsprechen jedoch weder dem Iterator-Protokoll noch dem iterierbaren Protokoll.
Jeder dieser Iteratoren verfügt über ein eigenes Prototypobjekt, das die vom jeweiligen Iterator verwendete next()-Methode definiert. Beispielsweise erben alle String-Iteratorobjekte von einem verborgenen Objekt StringIteratorPrototype, das über eine next()-Methode verfügt, welche diesen String anhand von Codepunkten iteriert. StringIteratorPrototype verfügt außerdem über eine [Symbol.toStringTag]-Eigenschaft, deren Anfangswert der String "String Iterator" ist. Diese Eigenschaft wird in Object.prototype.toString() verwendet. Ebenso besitzen andere Iterator-Prototypen eigene [Symbol.toStringTag]-Werte, die den oben angegebenen Namen entsprechen.
Alle diese Prototypobjekte erben von Iterator.prototype, das eine [Symbol.iterator]()-Methode bereitstellt, die das Iterator-Objekt selbst zurückgibt. Dadurch wird der Iterator auch iterierbar.
Iterator-Hilfsmethoden
Hinweis:
Diese Methoden sind Iterator-Hilfsmethoden und keine iterierbaren Hilfsmethoden, da die einzige Voraussetzung dafür, dass ein Objekt iterierbar ist, lediglich das Vorhandensein einer [Symbol.iterator]()-Methode ist. Es gibt keinen gemeinsamen Prototyp, auf dem diese Methoden installiert werden könnten.
Die Klasse Iterator selbst stellt einige Hilfsmethoden für die Arbeit mit Iteratoren bereit. Beispielsweise könnten Sie versucht sein, Folgendes zu tun:
const nameToDeposit = new Map([
["Anne", 1000],
["Bert", 1500],
["Carl", 2000],
]);
const totalDeposit = [...nameToDeposit.values()].reduce((a, b) => a + b);
Dadurch wird der von Map.prototype.values() zurückgegebene Iterator zunächst in ein Array umgewandelt und dann die Methode Array.prototype.reduce() verwendet, um die Summe zu berechnen. Dies erzeugt jedoch sowohl ein Zwischenarray als auch eine zweimalige Iteration über das Array. Stattdessen können Sie die reduce()-Methode des Iterators selbst verwenden:
const totalDeposit = nameToDeposit.values().reduce((a, b) => a + b);
Diese Methode kann effizienter sein, insbesondere hinsichtlich des Speicherverbrauchs, da sie den Iterator nur einmal durchläuft, ohne Zwischenwerte zu speichern. Iterator-Hilfsmethoden sind notwendig, um mit unendlichen Iteratoren zu arbeiten:
function* fibonacci() {
let current = 1;
let next = 1;
while (true) {
yield current;
[current, next] = [next, current + next];
}
}
const seq = fibonacci();
const firstThreeDigitTerm = seq.find((n) => n >= 100);
Sie können seq nicht in ein Array umwandeln, weil es unendlich ist. Stattdessen können Sie die find()-Methode des Iterators selbst verwenden, die seq nur so weit durchläuft, wie es nötig ist, um den ersten Wert zu finden, der die Bedingung erfüllt.
Sie finden viele Iterator-Methoden, die Array-Methoden entsprechen, beispielsweise:
Iterator.prototype.drop() und Iterator.prototype.take() entsprechen in Kombination in gewisser Weise Array.prototype.slice().
Iterator-Hilfsobjekte
Hinweis: Iterator-Hilfsobjekte und Iterator-Hilfsmethoden sind zwei unterschiedliche Konzepte. Ein Iterator-Hilfsobjekt kann zur Laufzeit erkannt werden, während „Iterator-Hilfsmethode“ lediglich eine Bezeichnung für eine Reihe von Methoden zum besseren Verständnis ist. Iterator-Hilfsmethode kann je nach Kontext entweder das Objekt oder die Methode bezeichnen.
Unter den Iterator-Hilfsmethoden geben filter(), flatMap(), map(), drop() und take() ein neues Iterator Helper-Objekt zurück. Der Iterator Helper ist ebenfalls eine Iterator-Instanz, wodurch diese Hilfsmethoden verkettbar sind. Alle Iterator-Hilfsobjekte erben von einem gemeinsamen Prototypobjekt, das das Iterator-Protokoll implementiert:
next()-
Ruft die
next()-Methode des zugrunde liegenden Iterators auf, wendet die Hilfsmethode auf das Ergebnis an und gibt das Ergebnis zurück. return()-
Ruft die
return()-Methode des zugrunde liegenden Iterators auf und gibt das Ergebnis zurück.
Der Iterator Helper verwendet dieselbe Datenquelle wie der zugrunde liegende Iterator, sodass das Iterieren des Iterator Helper auch zur Iteration des zugrunde liegenden Iterators führt. Es gibt keine Möglichkeit, einen Iterator „aufzuspalten“, damit er mehrfach iteriert werden kann.
const it = [1, 2, 3].values();
const it2 = it.drop(0); // Essentially a copy
console.log(it.next().value); // 1
console.log(it2.next().value); // 2
console.log(it.next().value); // 3
Korrekte Iteratoren
Es gibt zwei Arten von „Iteratoren“: Objekte, die dem Iterator-Protokoll entsprechen (was mindestens nur das Vorhandensein einer next()-Methode erfordert), und Objekte, die von der Klasse Iterator erben und die Hilfsmethoden nutzen können. Das eine bedingt nicht das andere — Objekte, die von Iterator erben, werden nicht automatisch zu Iteratoren, da die Klasse Iterator keine next()-Methode definiert. Stattdessen muss das Objekt selbst eine next()-Methode definieren. Ein korrekter Iterator entspricht sowohl dem Iterator-Protokoll als auch erbt er von Iterator. Der meiste Code erwartet, dass Iteratoren korrekte Iteratoren sind und iterierbare Objekte korrekte Iteratoren zurückgeben. Um korrekte Iteratoren zu erstellen, definieren Sie eine Klasse, die Iterator erweitert, oder verwenden Sie die Methode Iterator.from().
class MyIterator extends Iterator {
next() {
// …
}
}
const myIterator = Iterator.from({
next() {
// …
},
});
Konstruktor
Iterator()-
Dazu vorgesehen, von anderen Klassen erweitert zu werden, die Iteratoren erstellen. Löst einen Fehler aus, wenn er eigenständig konstruiert wird.
Statische Methoden
Iterator.concat()-
Erstellt ein neues
Iterator-Objekt aus einer Liste iterierbarer Objekte. Der neue Iterator liefert die Werte jedes Eingabe-Iterables nacheinander. Iterator.from()-
Erstellt ein neues
Iterator-Objekt aus einem Iterator oder iterierbaren Objekt. Iterator.zip()-
Erstellt ein neues
Iterator-Objekt, das Elemente mehrerer iterierbarer Objekte zusammenfasst, indem es Arrays mit Elementen an derselben Position liefert. Iterator.zipKeyed()-
Erstellt ein neues
Iterator-Objekt, das Elemente mehrerer iterierbarer Objekte zusammenfasst, indem es Objekte mit Elementen an derselben Position und den durch die Eingabe angegebenen Schlüsseln liefert.
Instanzeigenschaften
Diese Eigenschaften sind auf Iterator.prototype definiert und werden von allen Iterator-Instanzen gemeinsam verwendet.
Iterator.prototype.constructor-
Die Konstruktorfunktion, die das Instanzobjekt erstellt hat. Für
Iterator-Instanzen ist der Anfangswert der KonstruktorIterator. Iterator.prototype[Symbol.toStringTag]-
Der Anfangswert der
[Symbol.toStringTag]-Eigenschaft ist der String"Iterator". Diese Eigenschaft wird inObject.prototype.toString()verwendet.Hinweis: Im Gegensatz zu
[Symbol.toStringTag]bei den meisten integrierten Klassen istIterator.prototype[Symbol.toStringTag]aus Gründen der Webkompatibilität beschreibbar.
Instanzmethoden
Iterator.prototype.chunks()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das die Elemente des ursprünglichen Iterators in aufeinanderfolgende Array-Blöcke aufteilt. Jedes Mal, wenn das Hilfsobjekt iteriert wird, ruft es die angegebene Anzahl an Elementen vom zugrunde liegenden Iterator ab und liefert sie gemeinsam.
Iterator.prototype.drop()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das die angegebene Anzahl von Elementen am Anfang dieses Iterators überspringt.
Iterator.prototype.every()-
Gibt
falsezurück, wenn ein Element gefunden wird, das die bereitgestellte Testfunktion nicht erfüllt. Andernfalls wirdtruezurückgegeben, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden. Iterator.prototype.filter()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das nur jene Elemente des Iterators liefert, für die die bereitgestellte Callback-Funktion
truezurückgibt. Iterator.prototype.find()-
Gibt das erste vom Iterator erzeugte Element zurück, das die bereitgestellte Testfunktion erfüllt. Wenn keine Werte die Testfunktion erfüllen, wird
undefinedzurückgegeben. Iterator.prototype.flatMap()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das jedes Element im ursprünglichen Iterator durch eine Mapping-Funktion verarbeitet und die von der Mapping-Funktion zurückgegebenen Elemente liefert, die in einem anderen Iterator oder iterierbaren Objekt enthalten sind.
Iterator.prototype.forEach()-
Führt eine bereitgestellte Funktion einmal für jedes vom Iterator erzeugte Element aus.
Iterator.prototype.includes()-
Gibt
truezurück, wenn ein vom Iterator erzeugtes Element dem angegebenen Wert entspricht. Andernfalls wirdfalsezurückgegeben, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden. Iterator.prototype.join()-
Gibt einen String zurück, der die Verkettung aller vom Iterator erzeugten Elemente darstellt, getrennt durch Kommas oder einen angegebenen Trennzeichen-String.
Iterator.prototype.map()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das Elemente des Iterators liefert, die jeweils durch eine Mapping-Funktion transformiert wurden.
Iterator.prototype.reduce()-
Führt für jedes vom Iterator erzeugte Element eine benutzerdefinierte „Reducer“-Callback-Funktion aus und übergibt dabei den Rückgabewert aus der Berechnung des vorhergehenden Elements. Das Endergebnis der Ausführung des Reducers über alle Elemente ist ein einzelner Wert.
Iterator.prototype.some()-
Gibt
truezurück, wenn ein Element gefunden wird, das die bereitgestellte Testfunktion erfüllt. Andernfalls wirdfalsezurückgegeben, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden. Iterator.prototype.take()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das die angegebene Anzahl von Elementen dieses Iterators liefert und anschließend beendet wird.
Iterator.prototype.toArray()-
Erstellt eine neue
Array-Instanz, die mit den vom Iterator gelieferten Elementen gefüllt ist. Iterator.prototype.windows()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das ein gleitendes Fenster von Elementen liefert. Jedes Mal, wenn das Hilfsobjekt iteriert wird, liefert es ein Array, indem es das erste Element aus der vorherigen Iteration entfernt und das nächste Element aus dem ursprünglichen Iterator hinzufügt.
Iterator.prototype[Symbol.dispose]()-
Ruft die
return()-Methode vonthisauf, sofern sie existiert. Dies implementiert das Disposable-Protokoll und ermöglicht die Freigabe bei Verwendung mitusingoderawait using. Iterator.prototype[Symbol.iterator]()-
Gibt das Iterator-Objekt selbst zurück. Dadurch können Iterator-Objekte auch iterierbar sein.
Beispiele
>Einen Iterator als iterierbares Objekt verwenden
Alle integrierten Iteratoren sind auch iterierbar, sodass Sie sie in einer for...of-Schleife verwenden können:
const arrIterator = [1, 2, 3].values();
for (const value of arrIterator) {
console.log(value);
}
// Logs: 1, 2, 3
Spezifikationen
| Spezifikation |
|---|
| ECMAScript® 2027 Language Specification> # sec-iterator-objects> |