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 eingebauten Iteratoren erben von der Iterator-Klasse. Die Iterator-Klasse bietet eine [Symbol.iterator]()-Methode, die das Iterator-Objekt selbst zurückgibt, wodurch der Iterator ebenfalls iterierbar wird. Sie bietet auch einige Hilfsmethoden für die Arbeit mit Iteratoren.
Beschreibung
Die folgenden sind alle eingebauten 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
Generator-Objekt, das von generierenden Funktionen zurückgegeben wird. - 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 die Kern-JavaScript-Iteratoren wieder, während andere ihre eigenen Iteratoren definieren. Zum Beispiel:
- Array-ähnliche Objekte wie
NodeListgeben einen Array Iterator von ihren jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()zurück. - Map-ähnliche Objekte von Web-APIs wie
Headersgeben ihren eigenen Iteratortyp wie Headers Iterator von ihren jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()zurück. - Set-ähnliche Objekte von Web-APIs wie
FontFaceSetgeben ihren eigenen Iteratortyp wie FontFaceSet Iterator von ihren jeweiligen Methodenkeys(),values(),entries()und[Symbol.iterator]()zurück.
Hinweis:
NodeIterator und andere alte Schnittstellen sind zwar so benannt, entsprechen jedoch nicht dem Iterator-Protokoll oder dem Iterable-Protokoll.
Jeder dieser Iteratoren hat ein eigenes Prototyp-Objekt, das die next()-Methode definiert, die von dem jeweiligen Iterator verwendet wird. Zum Beispiel erben alle String-Iterator-Objekte von einem versteckten Objekt StringIteratorPrototype, das eine next()-Methode besitzt, die diesen String durch Codepunkte iteriert. StringIteratorPrototype hat auch eine [Symbol.toStringTag]-Eigenschaft, deren Anfangswert der String "String Iterator" ist. Diese Eigenschaft wird in Object.prototype.toString() verwendet. Ähnlich haben andere Iterator-Prototypen auch ihre eigenen [Symbol.toStringTag]-Werte, die mit den oben genannten Namen identisch sind.
Alle diese Prototyp-Objekte erben von Iterator.prototype, das eine [Symbol.iterator]()-Methode bereitstellt, die das Iterator-Objekt selbst zurückgibt und den Iterator dadurch ebenfalls iterierbar macht.
Iterator-Hilfsmethoden
Hinweis:
Diese Methoden sind Iterator-Hilfsmethoden, keine Iterable-Hilfsmethoden, da die einzige Anforderung für ein Objekt, iterierbar zu sein, lediglich das Vorhandensein einer [Symbol.iterator]()-Methode ist. Es gibt keinen gemeinsamen Prototyp, um diese Methoden zu installieren.
Die Iterator-Klasse selbst bietet einige Hilfsmethoden für die Arbeit mit Iteratoren an. Zum Beispiel 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);
Dies konvertiert zuerst den von Map.prototype.values() zurückgegebenen Iterator in ein Array und verwendet dann die Array.prototype.reduce()-Methode, um die Summe zu berechnen. Dies erzeugt jedoch sowohl ein Zwischen-Array als auch iteriert das Array zweimal. Stattdessen können Sie die reduce()-Methode des Iterators selbst verwenden:
const totalDeposit = nameToDeposit.values().reduce((a, b) => a + b);
Diese Methode kann möglicherweise effizienter sein, insbesondere speichermäßig, da sie den Iterator nur einmal iteriert, ohne irgendwelche Zwischenergebnisse 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 konvertieren, da es unendlich ist. Stattdessen können Sie die find()-Methode des Iterators selbst verwenden, die seq nur so weit iteriert, wie es notwendig ist, um den ersten Wert zu finden, der die Bedingung erfüllt.
Sie werden viele Iterator-Methoden finden, die Analogien zu Array-Methoden aufweisen, wie zum Beispiel:
Iterator.prototype.drop() und Iterator.prototype.take() zusammen sind einigermaßen analog zu Array.prototype.slice().
Iterator-Hilfsobjekte
Hinweis: Iterator-Hilfsobjekte und Iterator-Hilfsmethoden sind zwei verschiedene Konzepte. Ein Iterator-Hilfsobjekt ist zur Laufzeit erkennbar, während "Iterator-Hilfsmethode" nur ein Name für ein Set von Methoden zur Verständlichkeit ist. Iterator-Hilfsobjekt kann sich je nach Kontext entweder auf das Objekt oder die Methode beziehen.
Unter den Iterator-Hilfsmethoden erzeugen filter(), flatMap(), map(), drop(), und take() ein neues Iterator-Hilfsobjekt. Der Iterator-Hilfsobjekt ist ebenfalls eine Instanz von Iterator, was diese Hilfsmethoden kettefähig macht. Alle Iterator-Hilfsobjekte erben von einem gemeinsamen Prototyp-Objekt, 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-Hilfsobjekt teilt die gleiche Datenquelle wie der zugrunde liegende Iterator, sodass die Iteration des Iterator-Hilfsobjekts auch den zugrunde liegenden Iterator iteriert. Es gibt keine Möglichkeit, einen Iterator "aufzuteilen", um ihn mehrmals zu iterieren.
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
Richtige Iteratoren
Es gibt zwei Arten von "Iteratoren": Objekte, die dem Iterator-Protokoll entsprechen (was im Minimalfall nur das Vorhandensein einer next()-Methode erfordert), und Objekte, die von der Iterator-Klasse erben und die Hilfsmethoden nutzen. Sie bedingen einander nicht — Objekte, die von Iterator erben, werden nicht automatisch zu Iteratoren, da die Iterator-Klasse keine next()-Methode definiert. Stattdessen muss das Objekt selbst eine next()-Methode definieren. Ein richtiger Iterator ist einer, der sowohl dem Iterator-Protokoll entspricht als auch von Iterator erbt, und die meisten Codes erwarten, dass Iteratoren richtige Iteratoren sind und Iterables richtige Iteratoren zurückgeben. Um richtige Iteratoren zu erstellen, definieren Sie eine Klasse, die Iterator erweitert, oder verwenden Sie die Iterator.from()-Methode.
class MyIterator extends Iterator {
next() {
// …
}
}
const myIterator = Iterator.from({
next() {
// …
},
});
Konstruktor
Iterator()-
Soll von anderen Klassen erweitert werden, die Iteratoren erstellen. Löst einen Fehler aus, wenn er selbst konstruiert wird.
Statische Methoden
Iterator.concat()-
Erzeugt ein neues
Iterator-Objekt aus einer Liste von iterierbaren Objekten. Der neue Iterator liefert die Werte aus jedem der Eingabe-Iterables nacheinander. Iterator.from()-
Erzeugt ein neues
Iterator-Objekt aus einem Iterator oder einem iterierbaren Objekt. Iterator.zip()-
Erzeugt ein neues
Iterator-Objekt, das Elemente aus mehreren iterierbaren Objekten aggregiert, indem es Arrays bereitstellt, die Elemente an der gleichen Position enthalten. Iterator.zipKeyed()-
Erzeugt ein neues
Iterator-Objekt, das Elemente aus mehreren iterierbaren Objekten aggregiert, indem es Objekte bereitstellt, die Elemente an der gleichen Position enthalten, mit Schlüsseln, die durch die Eingabe angegeben sind.
Instanz-Eigenschaften
Diese Eigenschaften sind auf Iterator.prototype definiert und werden von allen Iterator-Instanzen geteilt.
Iterator.prototype.constructor-
Die Konstrukturfunktion, die das Instanz-Objekt erstellt hat. Für
Iterator-Instanzen ist der Anfangswert derIterator-Konstruktor. Iterator.prototype[Symbol.toStringTag]-
Der Anfangswert der
[Symbol.toStringTag]-Eigenschaft ist der String"Iterator". Diese Eigenschaft wird inObject.prototype.toString()verwendet.Hinweis: Im Gegensatz zum
[Symbol.toStringTag]bei den meisten eingebauten Klassen istIterator.prototype[Symbol.toStringTag]aus Gründen der Web-Kompatibilität beschreibbar.
Instanz-Methoden
Iterator.prototype.drop()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das die gegebene Anzahl von Elementen am Anfang dieses Iterators überspringt.
Iterator.prototype.every()-
Gibt
falsezurück, wenn es ein Element findet, das die gegebene Testfunktion nicht erfüllt. Andernfalls, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden, gibt ertruezurück. Iterator.prototype.filter()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das nur jene Elemente des Iterators liefert, für die die gegebene Callback-Funktion
truezurückgibt. Iterator.prototype.find()-
Gibt das erste vom Iterator produzierte Element zurück, das die gegebene 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 nimmt, es durch eine Abbildungsfunktion leitet und die von der Abbildungsfunktion zurückgegebenen Elemente liefert (die sich in einem anderen Iterator oder iterierbaren Objekt befinden).
Iterator.prototype.forEach()-
Führt eine gegebene Funktion einmal für jedes vom Iterator produzierte Element aus.
Iterator.prototype.includes()-
Gibt
truezurück, wenn ein vom Iterator produziertes Element gleich dem angegebenen Wert ist. Andernfalls, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden, gibt erfalsezurück. Iterator.prototype.map()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das Elemente des Iterators liefert, die jeweils durch eine Abbildungsfunktion transformiert werden.
Iterator.prototype.reduce()-
Führt eine vom Benutzer gelieferte "Reducer"-Callback-Funktion auf jedem vom Iterator produzierten Element aus, wobei der Rückgabewert aus der Berechnung des vorhergehenden Elements übergeben wird. Das endgültige Ergebnis des Ausführens des Reducers über alle Elemente ist ein einzelner Wert.
Iterator.prototype.some()-
Gibt
truezurück, wenn es ein Element findet, das die gegebene Testfunktion erfüllt. Andernfalls, wenn der Iterator erschöpft ist, ohne ein solches Element zu finden, gibt erfalsezurück. Iterator.prototype.take()-
Gibt ein neues Iterator-Hilfsobjekt zurück, das die gegebene Anzahl von Elementen in diesem Iterator liefert und dann beendet.
Iterator.prototype.toArray()-
Erzeugt eine neue
Array-Instanz, die mit den vom Iterator gelieferten Elementen gefüllt ist. Iterator.prototype[Symbol.dispose]()-
Ruft die
return()-Methode vonthisauf, falls vorhanden. Dies implementiert das disposable Protocol und erlaubt es, entsorgt zu werden, wenn es mitusingoderawait usingverwendet wird. Iterator.prototype[Symbol.iterator]()-
Gibt das Iterator-Objekt selbst zurück. Dies ermöglicht es Iterator-Objekten, ebenfalls iterierbar zu sein.
Beispiele
>Verwenden eines Iterators als Iterable
Alle eingebauten Iteratoren sind ebenfalls 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-%iteratorprototype%-object> |