ES6#3 Destrukturyzacja, czyli nowe podejście do tablic i obiektów

W serii poświęconej standardowi ES6 języka JavaScript opisałem już pojawiające się tam słowo kluczowe class, pokazałem przykłady zastosowania let oraz const. Tym razem zajmiemy się destrukturyzacją i różnicami między operatorem spread i rest. Umożliwiają one użycie nowego sposobu obsługiwania tablic oraz obiektów, który jest szybszy, łatwiejszy oraz precyzyjniejszy. Możemy dzięki nim wydobywać najróżniejsze, nawet zagnieżdżone wartości, przy użyciu skróconego zapisu. Zaczynajmy!

Jeśli nie czytałeś jeszcze wcześniejszych części, to rzuć okiem na http://www.idaszak.com/article/2017/04/05/es6-2-var-let-const,
ponieważ w poniższym kodzie będziemy korzystać z let oraz const. Zapraszam także do zapoznania się z klasami w ES6:
http://www.idaszak.com/article/2017/04/02/czy-javascript-jest-obiektowy

# Destrukturyzacja tablic

Standardowym podejsciem do obsługi tablic, jest odwoływanie się do poszczególnych jej elementów za pomocą operatora []:

 
var array = ["raz","dwa","trzy"];
var first = array[0]; 
var second = array[1]; 
var third = array[2]; 
console.log(first, second, third); //"raz" "dwa" "trzy"

Dzięki destrukturyzacji, możemy zapisać to w dużo prostszy i bardziej zwięzły sposób:

 
const [first, second, third] = array;
console.log(first, second, third); //"raz", "dwa", "trzy"

Nie musimy przypisywać do zmiennej każdego z elementów, możemy je pomijać:

 
const [x, ,z] = array;
console.log(x, z); //"raz" "trzy"
const [,y] = array;
console.log(y); //"dwa"

Jak wygląda prosty przykład zastosowania destrukturyzacji tablicy? Możemy bez wykorzystywania zmiennej tymczasowej zamienić wartości dwóch zmiennych:

 
var a = 1, b = 2;
[b, a] = [a, b];
console.log(a, b);//2 1

Kolejną funkcjonalnością ES6 w odwoływaniu się do elementów tablicy jest operator spread ..., dzięki któremu możemy dotrzeć do pozostałych elementów, poza wybranymi:

 
const arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
const [a, b, c, d, ...others] = arr;
console.log(a); //1
console.log(others) //[5, 6, 7, 8, 9, 10]

Możemy wykonać także kolejną dekonstrukcję wybranego elementu:

 
const arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
const [x, y, ...[z, , ...rest] = arr;
console.log(rest); //[5, 6, 7, 8, 9, 10]
console.log(z); //3

Zastosowanie operatora spread? ES5 umożliwił korzystanie z funkcji .concat dla tablicy, co wygląda w taki sposób:

 
var boys = ["Kyle", "Douglas", "Matt"];
var girls = ["Rebecca","Kate"];
var people = boys.concat(girls);
console.log(people); //["Kyle", "Douglas", "Matt", "Rebecca", "Kate"]

W ES6 możemy skorzystać z operatora spread, co wygląda znacznie czytelniej:

 
let people = [...boys, ...girls];
console.log(people); //["Kyle", "Douglas", "Matt", "Rebecca", "Kate"]

# Destrukturyzacja obiektów

Destrukturyzacja obiektów jest bardzo podobna do destrukturyzacji tablic, z tą różnicą, że korzystamy z nazwy kluczy obiektu:

 
const object = {a: "1", b: "2", c: "3"};
const {a, c} = object;
console.log(a, c);//1 3

Możemy też stworzyć klucz, dzięki któremu dodamy kolejną wartość do tablicy:

 
const key = "d";
object[key] = "4";
console.log(object);// {a: "1", b: "2", c: "3", d: "4"}

Analogicznie do destrukturyzacji tablic, w obiektach możemy odwoływać się do zagnieżdżonych wartości:

 
const obj = {x: {y: "5", z: "6"}};
const {x: {z: value}} = obj;
console.log(value);//6

Możemy także korzystać z operatora spread ...:

 
const object = {a: "1", b: "2", c: "3"};
const {a, ...others} = object;
console.log(others); //{b: "2", c: "3"}

# Spread a Rest?

Poznaliśmy już operator spread, który umożliwia nam rozszerzenie zmiennej na wiele elementów, która działa zarówno na tablicach jak i funkcjach. Jednak w ES6 jest jeszcze jeden operator składający się z trzech kropek.

rest to operator o jakby przeciwstawnym działaniu, dlatego że pozwala na zamknięcie dowolnej ilości argumentów funkcji w jedną tablicę.

Żeby dowiedzieć się, jak działa operator rest ... i jakie ma zastosowanie, stwórzmy sobie funkcję, która pozwoli na dodanie wszystkich argumentów przez nią przekazanych.

 
function add() {
  return arguments.reduce(function(previousValue, currentValue) {
      return previousValue + currentValue;
    });
}
add(1, 2, 3); // TypeError: arguments.reduce is not a function

arguments to tablica, zawierająca wszystkie przekazane argumenty. Wykonujemy na niej funkcję reduce, która skraca nam naszą tablicę zgodnie z wzorem w podanej jako argument funkcji, czyli w tym przypadku dodaje każdy kolejny element.

Niestety, tak napisany kod nie działa, jednak można naprawić go funkcją rest ...

 
function add(...numbers) {
  return numbers.reduce(function(previousValue, currentValue) {
      return previousValue + currentValue;
    });
}
add(1, 2, 3); // 6

W tym przypadku dowolna ilość argumentów przekazanych do funkcji może zostać użyta do stworzenia ich sumy.

Published: April 14 2017

blog comments powered by Disqus