map()
import React from 'react';
const Iteration = () => {
return(
<ol>
<li> Java </li>
<li> Python </li>
...
</ol>
);
}
export default Iteration;
React에서 위와 같이 반복되는 요소가 나타나면 어떻게 처리할까? React는 배열 객체의 내장 함수인 map 함수를 사용하여 주로 반복되는 컴포넌트를 렌더링한다. 먼저 map() 함수의 형식은 아래와 같다.
// 형식 arr.map(callback, [thisArg]);
const arr = [1,2,3,4,5];
const newArr = arr.map((num)=>{return num*num;});
callback 은 새로운 배열의 요소를 생성하는 콜백 함수를 의미하며, 아래 세가지의 매개변수를 갖는다.
- currentValue : 현재 처리하고 있는 요소
- index : 현재 처리하고 있는 요소의 index 값 (생략 가능)
- array : 현재 처리하고 있는 원본 배열 (생략가능)
thisArg 는 선택적으로 입력 가능하며, callback 함수 내부에서 사용할 this 레퍼런스를 의미한다. 클래스형 컴포넌트 등에서 bind할 때 사용한다.
map함수는 매개변수를 이용해 배열을 선언적으로 쉽게 다룰 수 있으며, React의 state 불변성 유지에 적합한 함수이다. 기존의 배열을 바탕으로 새로운 배열을 만들어 반환하기 때문이다.
요소와 컴포넌트의 반복
import React from 'react';
const Iteration = () => {
const names = ['Java', 'Python'];
const nameList = names.map((name,index) => <li key={index}>{name}</li>);
return(
<ul>{nameList}</ul>
);
}
export default Iteration;
React에서는 JSX(HTML 태그 및 컴포넌트)가 배열에 담길 경우 이를 차례로 출력해준다. 따라서 map() 함수로 JSX의 배열을 만들어 해당 요소나 컴포넌트를 반복시킬 수 있다.
주의해야할 것은 바로 key 값의 존재이다. React는 요소나 컴포넌트 배열을 렌더링할 때 때 해당 원소에 고유한 값인 key 값을 배정하고, 이를 바탕으로 어떤 원소에 변동이 있는지를 추적하려고 한다. 따라서 key값의 사용은 효과적인 탐색 및 렌더링을 돕는다. 배열 내부의 자료가 DB에서 불러왔다면 primary key, 아니라면 고유의 문자열을 사용한다. map함수에서 전달되는 index 를 사용할 수도 있지만, 동적 배열이거나 자료의 순서가 계속 바뀌는 등의 경우 예기치 못한 결과를 반환할 수 있다.
물론 key값을 입력하지 않아도 React는 잘 작동하며 오류가 아닌 경고메시지가 출력된다. key가 없을 때는 diffing 과정에서 리스트를 순차적으로 비교하여 감지하므로, 작동은 하지만 훨씬 비효율적인 과정을 거친다. 따라서 반드시 key를 입력해주도록 하자.
배열 추가 및 제거
import React from 'react';
const Iteration = () => {
const [names,setNames] = useState([
{id: 1, text: 'Java'},
{id: 2, text: 'Python'}
]);
const [inputText, setInputText] = useState('');
const [nextId, setNextId] = useState(5);
const onChange = e => setInputText(e.target.value);
const onClick = () => {
const newId = {id: nextId, text: inputText};
setNextId(nextId + 1);
setNames([...names, newId]);
setInputText('');
}
const onRemove = id => {
const nextNames = names.filter(name => name.id !== id);
setNames(nextNames);
}
const nameList = names.map(name =>
(<li key={name.id} onDoubleClick={() => onRemove(name.id)}>{name.text}</li>));
return(
<>
<input value={inputText} onChange={onChange} />
<button onClick={onClick}>추가</button>
<ul>{nameList}</ul>
...
</>
);
}
export default Iteration;
위의 예시는 input에 문자열을 입력하고 버튼을 클릭하면, 입력된 내용을 바탕으로 객체에 만들어 names 배열에 추가해준다. 또한 리스트를 더블 클릭하면 해당되는 객체가 names에서 삭제된다.
일반적으로 React에서 기존 배열에 요소를 추가할 때는 위에서 사용한 spread연산자나 concat 함수를 사용한다. 이들은 기존 배열을 바탕으로 새로운 배열을 반환하여 React의 상태 불변성을 유지한다.
기존 배열의 요소를 삭제할 때는 filter함수를 사용하여 불변성을 유지할 수 있다.
'Web > React' 카테고리의 다른 글
[React] 5-1. ref (1) | 2023.12.04 |
---|---|
[React] 4-1 이벤트 (1) | 2023.12.02 |
[React] 3-2. state (1) | 2023.11.29 |
[React] 3-1. 컴포넌트와 props (0) | 2023.11.27 |
[React] 2-2. JSX (2) | 2023.11.27 |