Sådan klones en matrix i JavaScript

JavaScript har mange måder at gøre noget på. Jeg har skrevet på 10 måder at skrive rør / komponere i JavaScript, og nu laver vi arrays.

1. Spread Operator (lav kopi)

Lige siden ES6 faldt, har dette været den mest populære metode. Det er en kort syntaks, og du finder det utroligt nyttigt, når du bruger biblioteker som React og Redux.

numbers = [1, 2, 3]; numbersCopy = [...numbers]; 

Bemærk: Dette kopierer ikke sikkert multidimensionelle arrays. Array- / objektværdier kopieres ved reference i stedet for efter værdi .

Det er fint

numbersCopy.push(4); console.log(numbers, numbersCopy); // [1, 2, 3] and [1, 2, 3, 4] // numbers is left alone 

Dette er ikke fint

nestedNumbers = [[1], [2]]; numbersCopy = [...nestedNumbers]; numbersCopy[0].push(300); console.log(nestedNumbers, numbersCopy); // [[1, 300], [2]] // [[1, 300], [2]] // They've both been changed because they share references 

2. Godt gammelt for () Loop (lav kopi)

Jeg forestiller mig, at denne tilgang er den mindst populære, i betragtning af hvordan trendy funktionel programmering bliver i vores kredse.

Ren eller uren, erklærende eller bydende, det får jobbet gjort!

numbers = [1, 2, 3]; numbersCopy = []; for (i = 0; i < numbers.length; i++) { numbersCopy[i] = numbers[i]; } 

Bemærk: Dette kopierer ikke sikkert multidimensionelle arrays. Da du bruger =operatøren, tildeler den objekter / arrays med reference i stedet for efter værdi .

Det er fint

numbersCopy.push(4); console.log(numbers, numbersCopy); // [1, 2, 3] and [1, 2, 3, 4] // numbers is left alone 

Dette er ikke fint

nestedNumbers = [[1], [2]]; numbersCopy = []; for (i = 0; i < nestedNumbers.length; i++) { numbersCopy[i] = nestedNumbers[i]; } numbersCopy[0].push(300); console.log(nestedNumbers, numbersCopy); // [[1, 300], [2]] // [[1, 300], [2]] // They've both been changed because they share references 

3. God gammel mens () sløjfe (lav kopi)

Samme som for—impure, bydende nødvendigt, bla, bla, bla ... det virker! ?

numbers = [1, 2, 3]; numbersCopy = []; i = -1; while (++i < numbers.length) { numbersCopy[i] = numbers[i]; } 

Bemærk: Dette tildeler også objekter / arrays ved reference i stedet for efter værdi .

Det er fint

numbersCopy.push(4); console.log(numbers, numbersCopy); // [1, 2, 3] and [1, 2, 3, 4] // numbers is left alone 

Dette er ikke fint

nestedNumbers = [[1], [2]]; numbersCopy = []; i = -1; while (++i < nestedNumbers.length) { numbersCopy[i] = nestedNumbers[i]; } numbersCopy[0].push(300); console.log(nestedNumbers, numbersCopy); // [[1, 300], [2]] // [[1, 300], [2]] // They've both been changed because they share references 

4. Array.map (lav kopi)

Tilbage i moderne område finder vi mapfunktionen. Forankret i matematik maper begrebet at omdanne et sæt til en anden type sæt, mens struktur bevares.

På engelsk betyder det, at du Array.mapreturnerer en matrix af samme længde hver eneste gang.

Brug mapmed en doublefunktion til at fordoble en liste med tal .

numbers = [1, 2, 3]; double = (x) => x * 2; numbers.map(double); 

Hvad med kloning ??

Sandt nok handler denne artikel om kloning af arrays. For at duplikere en matrix skal du bare returnere elementet i dit mapopkald.

numbers = [1, 2, 3]; numbersCopy = numbers.map((x) => x); 

Hvis du gerne vil være lidt mere matematisk, (x) => xkaldes identitet . Den returnerer den parameter, den er blevet givet.

map(identity) kloner en liste.

identity = (x) => x; numbers.map(identity); // [1, 2, 3] 

Bemærk: Dette tildeler også objekter / arrays ved reference i stedet for efter værdi .

5. Array.filter (lav kopi)

Denne funktion returnerer et array, ligesom map, men det garanteres ikke at have samme længde.

Hvad hvis du filtrerer efter lige tal?

[1, 2, 3].filter((x) => x % 2 === 0); // [2] 

Indgangsarraylængden var 3, men den resulterende længde er 1.

Hvis dit filterprædikat altid vender tilbage true, får du dog et duplikat!

numbers = [1, 2, 3]; numbersCopy = numbers.filter(() => true); 

Hvert element består testen, så det returneres.

Bemærk: Dette tildeler også objekter / arrays ved reference i stedet for efter værdi .

6. Array.reduce (lav kopi)

Jeg har det næsten dårligt at bruge reducetil at klone et array, fordi det er så meget mere kraftfuldt end det. Men her går vi ...

numbers = [1, 2, 3]; numbersCopy = numbers.reduce((newArray, element) => { newArray.push(element); return newArray; }, []); 

reduce transformerer en startværdi, når den løber gennem en liste.

Her er den oprindelige værdi et tomt array, og vi udfylder det med hvert element, mens vi går. Denne matrix skal returneres fra den funktion, der skal bruges i den næste iteration.

Bemærk: Dette tildeler også objekter / arrays ved reference i stedet for efter værdi .

7. Array.slice (lav kopi)

slicereturnerer en lav kopi af en matrix baseret på det angivne start / slut-indeks, du angiver.

Hvis vi vil have de første 3 elementer:

[1, 2, 3, 4, 5].slice(0, 3); // [1, 2, 3] // Starts at index 0, stops at index 3 

If we want all the elements, don’t give any parameters

numbers = [1, 2, 3, 4, 5]; numbersCopy = numbers.slice(); // [1, 2, 3, 4, 5] 

Note: This is a shallow copy, so it also assigns objects/arrays by reference instead of by value.

8. JSON.parse and JSON.stringify (Deep copy)

JSON.stringify turns an object into a string.

JSON.parse turns a string into an object.

Combining them can turn an object into a string, and then reverse the process to create a brand new data structure.

Note: This onesafely copies deeply nested objects/arrays!

nestedNumbers = [[1], [2]]; numbersCopy = JSON.parse(JSON.stringify(nestedNumbers)); numbersCopy[0].push(300); console.log(nestedNumbers, numbersCopy); // [[1], [2]] // [[1, 300], [2]] // These two arrays are completely separate! 

9. Array.concat (Shallow copy)

concat combines arrays with values or other arrays.

[1, 2, 3].concat(4); // [1, 2, 3, 4] [1, 2, 3].concat([4, 5]); // [1, 2, 3, 4, 5] 

If you give nothing or an empty array, a shallow copy’s returned.

[1, 2, 3].concat(); // [1, 2, 3] [1, 2, 3].concat([]); // [1, 2, 3] 

Note: This also assigns objects/arrays by reference instead of by value.

10. Array.from (Shallow copy)

Dette kan gøre ethvert iterabelt objekt til et array. At give en matrix returnerer en lav kopi.

numbers = [1, 2, 3]; numbersCopy = Array.from(numbers); // [1, 2, 3] 

Bemærk: Dette tildeler også objekter / arrays ved reference i stedet for efter værdi .

Konklusion

Nå, dette var sjovt?

Jeg forsøgte at klone ved hjælp af kun 1 trin. Du finder mange flere måder, hvis du anvender flere metoder og teknikker.