GeezerVison is showing developer.mozilla.org — Array.prototype.flatMap() - JavaScript | MDN
Array.prototype.flatMap()
Baseline
Weitgehend verfügbar
Diese Funktion ist gut etabliert und funktioniert auf vielen Geräten und in vielen Browserversionen. Sie ist seit Januar 2020 browserübergreifend verfügbar.
Die Methode flatMap() von Array-Instanzen gibt ein neues Array zurück. Dazu wendet sie eine angegebene Callback-Funktion auf jedes Element des Arrays an und verflacht das Ergebnis anschließend um eine Ebene. Dies entspricht einem Aufruf von map() gefolgt von flat() mit Tiefe 1 (arr.map(...args).flat()), ist aber etwas effizienter, als die beiden Methoden getrennt aufzurufen.
const arr = [1, 2, 1];
const result = arr.flatMap((num) => (num === 2 ? [2, 2] : 1));
console.log(result);
// Expected output: Array [1, 2, 2, 1]
js flatMap(callbackFn)
flatMap(callbackFn, thisArg)
callbackFn
-
Eine Funktion, die für jedes Element im Array ausgeführt wird. Sie sollte entweder ein Array mit neuen Elementen für das neue Array oder einen einzelnen Wert, der kein Array ist und dem neuen Array hinzugefügt wird, zurückgeben. Die Funktion wird mit den folgenden Argumenten aufgerufen:
element
-
Das aktuelle Element, das im Array verarbeitet wird.
index
-
Der Index des aktuellen Elements, das im Array verarbeitet wird.
array
-
Das Array, auf dem flatMap() aufgerufen wurde.
thisArg Optional
-
Ein Wert, der beim Ausführen von callbackFn als this verwendet wird. Siehe iterative Methoden.
Ein neues Array, dessen Elemente die Ergebnisse der Callback-Funktion sind und das um eine Ebene verflacht wurde.
Die Methode flatMap() ist eine iterative Methode. Eine ausführliche Beschreibung der Callback-Funktion finden Sie unter Array.prototype.map(). Die Methode flatMap() entspricht map(callbackFn, thisArg) gefolgt von flat(1): Sie erzeugt für jedes Element ein Array neuer Elemente und verkettet die resultierenden Arrays zu einem neuen Array. Weitere Informationen zur allgemeinen Funktionsweise dieser Methoden finden Sie im Abschnitt über iterative Methoden.
Die Methode flatMap() ist generisch. Sie setzt lediglich voraus, dass der Wert von this eine length-Eigenschaft und Eigenschaften mit ganzzahligen Schlüsseln besitzt. Damit der von callbackFn zurückgegebene Wert verflacht wird, muss er allerdings ein Array sein.
Speicher vorab reservieren und explizit iterieren
js const arr = [1, 2, 3, 4];
arr.flatMap((x) => [x, x * 2]);
// is equivalent to
const n = arr.length;
const acc = new Array(n * 2);
for (let i = 0; i < n; i++) {
const x = arr[i];
acc[i * 2] = x;
acc[i * 2 + 1] = x * 2;
}
// [1, 2, 2, 4, 3, 6, 4, 8]
Beachten Sie, dass der Ansatz mit flatMap in diesem speziellen Fall langsamer ist als der Ansatz mit einer for-Schleife. Der Grund dafür sind temporäre Arrays, die von der Garbage Collection bereinigt werden müssen, sowie die Tatsache, dass die Größe des Ergebnis-Arrays nicht häufig angepasst werden muss. Dennoch kann flatMap die richtige Lösung sein, wenn seine Flexibilität und Lesbarkeit gefragt sind.
js const arr = [1, 2, 3, 4];
arr.map((x) => [x * 2]);
// [[2], [4], [6], [8]]
arr.flatMap((x) => [x * 2]);
// [2, 4, 6, 8]
// only one level is flattened
arr.flatMap((x) => [[x * 2]]);
// [[2], [4], [6], [8]]
Das obige Ergebnis hätte sich auch allein mit map erzielen lassen. Das folgende Beispiel veranschaulicht die Verwendung von flatMap() besser.
Erstellen wir aus einer Liste von Sätzen eine Liste von Wörtern.
js const arr = ["it's Sunny in", "", "California"];
arr.map((x) => x.split(" "));
// [["it's","Sunny","in"],[""],["California"]]
arr.flatMap((x) => x.split(" "));
// ["it's","Sunny","in", "", "California"]
Beachten Sie, dass die Länge der Ausgabeliste von der Länge der Eingabeliste abweichen kann.
Mit flatMap können Sie während eines map-Aufrufs Elemente hinzufügen und entfernen, also die Anzahl der Elemente ändern. Anders ausgedrückt: Statt Elemente immer eins zu eins abzubilden, können Sie viele Elemente auf viele Elemente abbilden, indem Sie jedes Eingabeelement einzeln verarbeiten. In diesem Sinne funktioniert es wie das Gegenstück zu filter. Geben Sie ein Array mit einem Element zurück, um das Element beizubehalten, ein Array mit mehreren Elementen, um Elemente hinzuzufügen, oder ein leeres Array, um das Element zu entfernen.
js // Let's say we want to remove all the negative numbers
// and split the odd numbers into an even number and a 1
const a = [5, 4, -3, 20, 17, -33, -4, 18];
// |\ \ x | | \ x x |
// [4,1, 4, 20, 16, 1, 18]
const result = a.flatMap((n) => {
if (n < 0) {
return [];
}
return n % 2 === 0 ? [n] : [n - 1, 1];
});
console.log(result); // [4, 1, 4, 20, 16, 1, 18]
Das Argument array ist nützlich, wenn Sie auf ein anderes Element des Arrays zugreifen möchten, insbesondere wenn keine Variable vorhanden ist, die auf das Array verweist. Im folgenden Beispiel werden zunächst mit filter() betriebsbereite Stationen ausgewählt. Anschließend wird mit flatMap() ein neues Array erstellt, dessen Elemente jeweils eine Station und die darauffolgende Station enthalten. Für die letzte Station wird ein leeres Array zurückgegeben, damit sie nicht im Ergebnis-Array erscheint.
js const stations = ["New Haven", "West Haven", "Milford (closed)", "Stratford"];
const line = stations
.filter((name) => !name.endsWith("(closed)"))
.flatMap((name, idx, arr) => {
// Without the arr argument, there's no way to easily access the
// intermediate array without saving it to a variable.
if (idx === arr.length - 1) return []; // last station has no next station
return [`${name} - ${arr[idx + 1]}`];
});
console.log(line); // ['New Haven - West Haven', 'West Haven - Stratford']
Das Argument array ist nicht das Array, das gerade erstellt wird. Von der Callback-Funktion aus kann nicht auf dieses Array zugegriffen werden.
callbackFn wird für unbelegte Positionen im Quell-Array nicht aufgerufen, da auch map() sie überspringt. flat() ignoriert außerdem unbelegte Positionen in den zurückgegebenen Arrays.
js console.log([1, 2, , 4, 5].flatMap((x) => [x, x * 2])); // [1, 2, 2, 4, 4, 8, 5, 10]
console.log([1, 2, 3, 4].flatMap((x) => [, x * 2])); // [2, 4, 6, 8]
Die Methode flatMap() liest die length-Eigenschaft von this und greift anschließend auf jede Eigenschaft zu, deren Schlüssel eine nichtnegative ganze Zahl kleiner als length ist. Ist der Rückgabewert der Callback-Funktion kein Array, wird er immer direkt an das Ergebnis-Array angehängt.
js const arrayLike = {
length: 3,
0: 1,
1: 2,
2: 3,
3: 4, // ignored by flatMap() since length is 3
};
console.log(Array.prototype.flatMap.call(arrayLike, (x) => [x, x * 2]));
// [1, 2, 2, 4, 3, 6]
// Array-like objects returned from the callback won't be flattened
console.log(
Array.prototype.flatMap.call(arrayLike, (x) => ({
length: 1,
0: x,
})),
);
// [ { '0': 1, length: 1 }, { '0': 2, length: 1 }, { '0': 3, length: 1 } ]
|