[React] 7. React hooks[3] - useReducer란?
- -
7. React hooks[3] - useReducer란?
안녕하세요. 갓대희 입니다. 이번 포스팅은 [ React hook 중 useReducer에 대한 내용 ] 입니다. : )
https://ko.reactjs.org/docs/hooks-effect.html
1. useReducer 훅이란?
- useState를 대체할 수 있는 함수이다.
- React에서 컴포넌트의 상태 관리를 위해 기본적으로 가장 많이 쓰이는 hook은 state이다.
- 좀 더 복잡한 상태 관리가 필요한 경우 reducer를 사용할 수 있다.
( 콜백대신 dispatch를 전달할 수 있기 때문이라고 볼 수 있는데, 이 부분은 이후 확인해 보자. )
- reducer는 이전 상태와 Action을 합쳐, 새로운 state를 만드는 조작을 말한다.
※ useReducer를 사용하기 위한 구성요소들은 다음과 같다.
1. useReducer 함수
import React, { useReducer } from "react";
const [state, dispatch] = useReducer(reducer, initialState, init);
1. state
- 컴포넌트에서 사용할 상태
2. dispatch 함수
- 첫번째 인자인 reducer 함수를 실행시킨다.
- 컴포넌트 내에서 state의 업데이트를 일으키키 위해 사용하는 함수
3. reducer 함수
- 컴포넌트 외부에서 state를 업데이트 하는 함수
- 현재state, action 객체를 인자로 받아, 기존의 state를 대체하여 새로운 state를 반환하는 함수
4. initialState
- 초기 state
5. init
- 초기 함수 (초기 state를 조금 지연해서 생성하기 위해 사용)
2. dispatch 함수
- reducer 함수를 실행 시킨다.
- action 객체를 인자로 받으며 action 객체는 어떤 행동인지를 나타내는 type 속성과 해당 행동과 관련된 데이터(payload)를 담고 있다.
- action을 이용하여 컴포넌트 내에서 state의 업데이트를 일으킨다.
※ action은 보통 하기 샘플 예시와 같이 사용 한다.
ex1) action type만 정의하여 사용
<button onClick={() => dispatch({ type: "INCREMENT" })}>증가</button>
ex2) action type과, 데이터를 정의하여 사용
<button onClick={() => dispatch({ type: "INCREMENT", payload: 1 })}>증가</button>
3. reducer 함수
- 상기 dispatch 함수에 의해 실행되며, 컴포넌트 외부에서 state를 업데이트 하는 로직을 담당 한다.
- 함수의 인자로는 state와 action을 받게 된다.
- state와 action을 활용하여 새로운 state를 반환 한다.
ex1) action type만 정의하여 사용
function reducer(state, action) {
switch (action.type) {
case "INCREMENT":
return { count: state.count + 1 };
case "DECREMENT":
return { count: state.count - 1 };
default:
throw new Error("unsupported action type: ", action.type);
}
}
ex2) action type과, 데이터를 정의하여 사용
function reducer(state, action) {
switch (action.type) {
case "INCREMENT":
return { count: state.count + action.payload };
case "DECREMENT":
return { count: state.count - action.payload };
default:
throw new Error("unsupported action type: ", action.type);
}
}
※ count 함수를 통해 사용 방법을 알아 보고, state를 활용한 예시랑도 비교해 보자.
ex1) init 함수를 사용하지 않는 counter 예시
import React, { useReducer } from "react";
function reducer(state, action) {
switch (action.type) {
case "INCREMENT":
return { count: state.count + action.payload };
case "DECREMENT":
return { count: state.count - action.payload };
default:
throw new Error("unsupported action type: ", action.type);
}
}
const Counter = () => {
const initialState = { count: 0 };
const [state, dispatch] = useReducer(reducer, initialState);
return (
<>
<h2>{state.count}</h2>
<button onClick={() => dispatch({ type: "INCREMENT", payload: 1 })}>
증가
</button>
<button onClick={() => dispatch({ type: "DECREMENT", payload: 1 })}>
감소
</button>
<button onClick={() => dispatch({ type: "kkkkkkkkk", payload: 1 })}>
에러
</button>
</>
);
};
export default Counter;
See the Pen reducer1 by goddaehee (@goddaehee) on CodePen.
ex2) init 함수를 사용하여 counter 예시
- 초기 state를 조금 지연해서 생성할 수 있다.
- init 함수를 세 번째 인자로 전달하면, 초기 state는 init(initialArg)에 설정될 것 이다.
import React, { useReducer } from "react";
function init(initialState) {
return { count: initialState };
}
function reducer(state, action) {
switch (action.type) {
case "INCREMENT":
return { count: state.count + action.payload };
case "DECREMENT":
return { count: state.count - action.payload };
case "RESET":
return init(action.payload);
default:
throw new Error("unsupported action type: ", action.type);
}
}
const Counter = ({ initialCount }) => {
const [state, dispatch] = useReducer(reducer, initialCount, init);
return (
<>
<h2>{state.count}</h2>
<button onClick={() => dispatch({ type: "RESET", payload: 0 })}>
초기화
</button>
<button onClick={() => dispatch({ type: "INCREMENT", payload: 1 })}>
증가
</button>
<button onClick={() => dispatch({ type: "DECREMENT", payload: 1 })}>
감소
</button>
<button onClick={() => dispatch({ type: "kkkkkkkkk", payload: 1 })}>
에러
</button>
</>
);
};
export default Counter;
See the Pen reducer2 by goddaehee (@goddaehee) on CodePen.
ex3) useState 사용
import React, { useState } from "react";
const Counter = ({ initialCount }) => {
const initial = initialCount ? initialCount : 0;
const [count, setCount] = useState(initial);
const onIncrease = () => {
setCount((count) => count + 1);
};
const onDecrease = () => {
setCount((count) => count - 1);
};
return (
<>
<h2>Count: {count}</h2>
<button onClick={() => setCount(initial)}>초기화</button>
<button onClick={onIncrease}>증가</button>
<button onClick={onDecrease}>감소</button>
</>
);
};
export default Counter;
- useReducer를 활용 한다면 좀더 복잡한 프로세스를 처리할 수 있을 것이다.
- 그리고 state를 변경하는 부분(Count를 감소, 증가 시키는 부분)이 useState와 같은 경우 내부에 위치하며, useReducer와 같은 경우 외부에 위치 한다.
ex) useState
ex) useReducer
'2. 웹개발 > React' 카테고리의 다른 글
[React] 7. React hooks[2] - useEffect란? (1) | 2022.03.06 |
---|---|
[React] 6. React Router (리액트 라우터) 사용하기 (5) | 2022.02.02 |
[React] 5. React에 CSS 적용하기 (0) | 2022.02.02 |
[React] 4. React 컴포넌트(5) - map() 반복문, 배열 컴포넌트 (0) | 2022.02.01 |
[React] 4. React 컴포넌트(4) - 이벤트 처리 방법 (1) | 2022.02.01 |
소중한 공감 감사합니다