spread 연산자와 map() 메서드

2021. 2. 21. 10:42Frontend/JS

 

아래 코드를 보고 두가지 의문점이 생겼습니다.

data = [{
	'name': '',
	'money': ''
}]


function doubleMoney() {
    data = data.map((user) => {
        return { ...user, money: user.money * 2 } 
    })
}

 

의문점

1.  . . . 이라는 spread연산자는 단순 복사개념이라 생각했지만, 위 코드는 user라는 데이터를 어디에서 가져오는지 모호했으며

2.  위 함수에서 return 된 값은 어떤 형태인지 궁금하다.

 

해답

2. return된 형태 =>  { name: 'xxx', money: 1000}

user는 map()메서드를 사용하면서 갖게 된 임의의 변수명입니다. user대신 person이란 변수명을 사용해도 전혀 문제없습니다. (내부의 값 xxx, 1000은 임의로 사용한 값입니다)

 

1. 즉 1번 의문점에 대해 바로 답이 나오는데, user는 data 변수가 기존에 보유한 name, money를 field로 갖게 됩니다.

이때 data 객체의 원소만 추출하여( 쉽게 생각해 {} 중괄호를 벗긴다 }, return 객체에 들어가게 된다.

 

 

Spread 연산자

Spread 는 펼치다의 뜻을 가집니다. 어떤 객체 혹은 배열을  펼쳐 내부의 값에 접근할 수 있는 연산자입니다.

 

const arr = [10, 20, 30, 40, 50]; 
console.log(arr); // [ 10, 20, 30, 40, 50 ] 
console.log(...arr); // 10, 20, 30, 40, 50 

3번째 줄에서, spread연산자는 배열 내의 개별 요소를 하나씩 return함을 알 수 있습니다.

아래와 같이 배열 변수를 할당하면 spread연산자로 리턴한 요소를 다시 배열에 담을 수도 있습니다.

const arr = [10, 20, 30, 40, 50]; 

const newArr = [...arr] 
// spread 연산자에 의해 기존 arr은 배열 밖으로 나오지만, newArr배열에 다시 할당된다.

console.log(newArr); // [ 10, 20, 30, 40, 50 ]

쉽게 생각하면, spread연산자는 배열/객체의 껍질( 대괄호[]나, 중괄호{} )를 벗겨내 return한다고 볼수있습니다.

 

처음 의문점이 들었던 복사 개념에 대해 어느정도 이해가 됐습니다.

기존 배열(arr)의 요소들을 개별적으로 꺼내어 다시 newArr에 할당하니 언뜻 배열의 복사처럼 이해될 수 있었습니다.

const animal = {
  name: '강아지'
};

const cuteAnimal = {
  ...animal,
  attribute: 'cute'
};


>>> cuteAnimal = { 
	name: '강아지',
	attribute: 'cute'
	}

spread 연산자와 map

let animals = [{
	name: '강아지',
	attribute: 'cute'
},
{
	name: '고양이',
	attribute: 'chic'
},
{
	name: '사자',
	attribute: '멋쟁이'
}];

animal 객체의 모든 attribute 필드를 '멋쟁이'로 바꾸고 싶거나, 혹은 모든 내부 객체에 새로운 필드를 추가하고 싶을 때, spread연산자와 map()메서드를 활용할 수 있습니다.

 

1) 모든 attribute 필드를 '멋쟁이'로 바꾸기

animals = animals.map(anim => {
	return{...anim, attribute:"멋쟁이"}
    }
)


>>>
0: {name: "강아지", attribute: "멋쟁이"}
1: {name: "고양이", attribute: "멋쟁이"}
2: {name: "사자", attribute: "멋쟁이"}

 

2) animals 내부 객체에 새로운 공통된 필드를 추가 (ex: age: 10을 추가)

animals = animals.map(anim => {
	return{...anim, age: 10}
    }
)


>>>
0: {name: "강아지", attribute: "멋쟁이", age: 10}
1: {name: "고양이", attribute: "멋쟁이", age: 10}
2: {name: "사자", attribute: "멋쟁이", age: 10}

 

위의 두 예시에서 spread연산자와 map()메서드를 함께 사용 법을 확인할 수 있었습니다. 우리가 rest API에서 데이터를 받아와 일련의 공통된 작업을 해야할 때, 위의 방법들은 강력한 효과를 낼 수 있습니다.