비구조화 할당 문법을 소개
정의
모질라 형님들의 문서에 의하면 '비구조화 할당(destructuring assignment) 구문은 배열이나 객체의 속성을 해체하여 그 값을 개별 변수에 담을 수 있게 하는 자바스크립트 표현식(expression)'입니다.
간단하게 정리하면 배열 [], 혹은 객체 {} 안의 값을 편하게 꺼내 쓸 수 있는 문법입니다.
기본 문법(배열)
배열에서의 적용은 아래와 같습니다.
[a1, a2, ...rest_a] = [1, 2, 3, 4, 5, 6, 7, 8, 9];console.log(a1); // 1console.log(a2); // 2console.log(rest_a); // [3, 4, 5, 6, 7, 8, 9]
좌항이 호출될 변수명 집합, 우항이 할당할 값 입니다.
좌항의 각 요소에는 같은 index를 가지는 배열값이 할당됩니다.
또한 전개 연산자( ... )를 사용하여 좌항에서 명시적으로 할당되지 않은 나머지 배열 값들을 사용할 수 있습니다.
그리고 var, let, const를 사용해 변수들의 유효 범위를 명시적으로 선언할 수 있습니다.
var [b1, b2, ...rest_b] = [1, 2, 3, 4, 5, 6, 7, 8, 9];let [c1, c2, ...rest_c] = [1, 2, 3, 4, 5, 6, 7, 8, 9];const [d1, d2, ...rest_d] = [1, 2, 3, 4, 5, 6, 7, 8, 9];
전개 연산자 이후에 변수를 입력하거나, 좌 우항이 다른 속성일 경우 에러가 발생합니다.
[a1, a2, ...rest_a, a3] = [1, 2, 3, 4, 5, 6, 7, 8, 9]; // error[a1, a2, ...rest_a] = {a1 : 10, a2: 20}; // error
기본 문법(객체)
객체에서의 적용은 아래와 같습니다.
var { a1, a2, ...rest_a } = { a1 : 10, a2 : 20, a3 : 30, a4 : 40 };console.log(a1); // 10console.log(a2); // 20console.log(rest_a); // { a3: 30, a4: 40 }
객체의 경우에는 우항의 key 값이 좌항의 변수명과 매칭됩니다.
배열과 마찬가지로 var, let, const가 적용 가능합니다.
원래의 key 값과 다른 이름의 변수를 사용하는 방법은 아래와 같습니다.
var { a1 : awesome_name, a2 : dumb , ...rest_a } = { a1 : 10, a2 : 20, a3 : 30, a4 : 40 };console.log(awesome_name); // 10console.log(dumb); // 20
나머지 값을 뜻하는 전개 연산자는 우항의 key에 영향을 받지 않기 때문에 ...rest_a : blah 와 같은 표현식은 무의미하며, 실제로 에러가 발생합니다.
또한 우항의 key값에 변수명으로 사용 불가능한 문자열이 있을경우 아래와 같은 방식으로 비구조화 할 수 있습니다.
var key = 'it is key';var { 'an-apple':an_apple, [key]:it_is_key } = { 'an-apple' : 10, 'it is key' : 20};console.log(an_apple); // 10console.log(it_is_key); // 20
다만 이 경우에는 'an-apple'과 매칭할 변수명(an_apple)을 작성하지 않으면 에러가 발생하게 됩니다.
마지막으로 객체 비구조화에서 주의해야 할 점은 변수 선언에 대한 명시(var, let, const)가 없을 경우 괄호를 사용하여 묶어주어야 한다는 것 입니다.
({ a, b } = { a : 10, b : 20});console.log(a); // 10console.log(b); // 20{ c, d } = { c : 30, d : 40}; // error
기본값 할당
비구조화의 범위를 벗어나는 값 할당을 시도하면 undefined를 반환하게 됩니다.
[a, b] = [10];console.log(a); // 10console.log(b); // undefinedvar {c, d} = { c : 20};console.log(c); // 20console.log(d); // undefined
이런 경우를 방어하기 위해 호출될 변수명들에 기본값 할당을 할 수 있습니다.
[a=10, b=20] = [10];console.log(a); // 10console.log(b); // 20var {c = 30, d : new_name = 40} = { };console.log(c); // 30console.log(new_name); // 40
위와 같은 방법으로 변수명들에 할당 연산자(=)를 사용하여 기본값 할당을 할 수 있습니다.
5, 7번 줄처럼 객체에서 새로운 변수명에 할당하는 방식에도 기본값 할당을 사용할 수 있습니다.
복사(copy)
전개 연산자를 사용하여 배열, 객체의 깊은 복사를 할 수 있습니다.
var arr = [1,2,3];var copy1 = arr;var [...copy2] = arr;var copy3 = [...arr];arr[0] = 'String';console.log(arr); // [ 'String', 2, 3 ]console.log(copy1); // [ 'String', 2, 3 ]console.log(copy2); // [ 1, 2, 3 ]console.log(copy3); // [ 1, 2, 3 ]
얕은 복사인 copy1은 arr을 참조하기 때문에 0번 요소가 변경되었지만 전개 연산자를 사용한 copy2, copy3는 깊은 복사가 된 것을 볼 수 있습니다.
객체 역시 전개 연산자로 깊은 복사를 사용할 수 있습니다.
무엇보다도 강력한 점은 복사와 함께 새로운 값을 할당할 수 있다는 점 입니다.
var prevState = {name: "yuddomack",birth: "1996-11-01",age: 22};var state = {...prevState,age: 23};console.log(state); // { name: 'yuddomack', birth: '1996-11-01', age: 23 }
위와 같이 ...prevState를 사용하여 기존 객체를 복사함과 동시에 age키에 새로운 값(23)을 할당할 수 있습니다.
리액트의 props나 state처럼 이전 정보를 이용하는 경우 유용하게 사용할 수 있습니다.
함수에서의 사용
함수의 파라미터 부분에서도 비구조화 할당을 사용할 수 있습니다.
이러한 문법은 특히 API 응답 값을 처리하는데에 유용하게 사용됩니다.
function renderUser({name, age, addr}){console.log(name);console.log(age);console.log(addr);}const users = [{name: 'kim', age: 10, addr:'kor'},{name: 'joe', age: 20, addr:'usa'},{name: 'miko', age: 30, addr:'jp'}];users.map((user) => {renderUser(user);});
마찬가지로 map함수의 파라미터에도 바로 사용할 수 있습니다.
const users = [{name: 'kim', age: 10, addr:'kor'},{name: 'joe', age: 20, addr:'usa'},{name: 'miko', age: 30, addr:'jp'}];users.map(({name, age, addr}) => {console.log(name);console.log(age);console.log(addr);});
for of 문
뿐만 아니라 배열 내 객체들은 for of 문을 사용하여 비구조화 할 수 있습니다.
const users = [{name: 'kim', age: 10, addr:'kor'},{name: 'joe', age: 20, addr:'usa'},{name: 'miko', age: 30, addr:'jp'}];for(var {name : n, age : a} of users){console.log(n);console.log(a);}
중첩된 객체 및 배열의 비구조화
중첩된 객체 및 배열 역시 비구조화 할 수 있습니다.
const kim = {name: 'kim',age: 10,addr: 'kor',friends: [{name: 'joe', age: 20, addr:'usa'},{name: 'miko', age: 30, addr:'jp'}]};var { name: userName, friends: [ ,{ name: jpFriend }] } = kim;console.log(userName); // kimconsole.log(jpFriend); // miko
friends 배열의 호출 변수를 명시하는 대신, 배열을 한번 더 비구조화한 모습이 시선을 강탈합니다.
출처 : https://yuddomack.tistory.com/entry/%EC%9E%90%EB%B0%94%EC%8A%A4%ED%81%AC%EB%A6%BD%ED%8A%B8-%EB%AC%B8%EB%B2%95-%EB%B9%84%EA%B5%AC%EC%A1%B0%ED%99%94-%ED%95%A0%EB%8B%B9
댓글 없음:
댓글 쓰기