useState Hook 개념
useState는 상태 변경이 일어나는 변수를 쉽고 편하게 관리하기 위한 React Hook이다.
useState는 원래 아래와 같은 배열을 반환한다.
[변수의 값, 변수를 변경(=set)하는 함수 이름]
배열을 반환하므로 각 인덱스를 직접 찍어보는 것도 가능하다.
const stateArray = useState()
console.log(stateArray[0]) // undefined
console.log(stateArray[1]) // function
여기서 상태 변수에 초기값을 할당하고 싶으면 useState 함수 인자로 초기값을 입력하면 된다.
const stateArray = useState("Hi Hello")
console.log(stateArray[0]) // "Hi Hello"
console.log(stateArray[1]) // function
인덱스를 직접 찍는 것보다 아래와 같이 배열을 구조 분해하여 할당하면 더 편하게 사용 가능하다. 가장 보편적이고 정석적인 사용 방법이다.
(아래 코드는 이 위 코드와 같은 기능을 한다)
const [state, setState] = useState("Hi Hello")
console.log(state) // "Hi Hello"
console.log(setState) // function
setState로 상태 업데이트하기 (1)
쉬운 예제로 counter를 만든다고 해보자. 사용자가 버튼을 클릭했을 때 state에 1을 더해주는 것이다. 그럼 아래와 같이 짤 수 있다.
const [state, setState] = useState(0)
const onClick = () => {
setState(state + 1)
}
그런데 개발하다보면 state 변경이 제대로 이루어지지 않는 상황을 마주하게 된다. 아 스쳐지나가는 옛 기억..
예를 들어, 똑같이 counter를 만드는데 버튼이 두 개라고 해보자. 버튼 A는 방금 위에서 했던 것처럼 눌리면 바로 1을 더해주는 거고, 버튼 B는 클릭된 시점에서 3초 이후에 1을 더하는 버튼이다.
const [state, setState] = useState(0)
const onClickA = () => {
setState(state + 1)
}
const onClickB = () => {
// 대충 setTimeout 써서 3초 기다리는 코드
setState(state + 1)
}
버튼 B를 누르고 기다리는 3초 동안에 버튼 A를 마구 누르면 state는 어떻게 될까? 'B를 누른 횟수 1회 + A를 누른 횟수 n회'가 되면 이상적일 것이다. 그러나 실제로는 1이 된다. 왜냐하면 onClickB 함수 내 state 변수는 함수가 호출된 시점의 state, 즉 0이기 때문이다. 버튼 A를 아무리 눌러도 B를 눌렀을 시점에 state의 값은 0이고, 3초 후에 state + 1 이 일어나므로 1이 되는 것이다.
이런 경우도 마찬가지이다.
const [state, setState] = useState(0)
const onClick = () => {
setState(state + 1) // 0 + 1
setState(state + 1) // 0 + 1
setState(state + 1) // 0 + 1
}
하나의 함수 내에서 "setState(state + 1)"를 여러 번 반복하고 있지만, state 값은 1이다. 이유는 위와 같다(호출 시점에 state가 0).
setState로 상태 업데이트하기 (2): Functional Update
setState에 함수를 넣으면 앞서 겪은 상황들을 해결할 수 있다. state + 1과 같이 상수가 아니라 함수를 넣어 업데이트 해주는 것이다.
const [state, setState] = useState(0)
const onClick = () => {
setState((currentState) => currentState + 1) // 0 + 1
setState((currentState) => currentState + 1) // 1 + 1
setState((currentState) => currentState + 1) // 2 + 1
}
setState에 집어넣은 함수의 인자 currentState는 자동으로 현재 state 값을 추적, 맵핑한다(이름이 currentState가 아니어도 됨).
즉 함수로 업데이트할 경우, 항상 최신값을 보장할 수 있다.
참고로 setState 함수는 원래 이렇게 생겼다.
setState(updater[, callback])
마무리
- React의 useState는 [상태 변수 값, 상태 변수를 변경할 함수]를 반환한다.
- setState 함수 인자로 state 값을 직접 넣는 경우, 호출 시점의 state 값이 사용된다.
- setState 함수 인자로 함수를 넣는 경우, 현재 state 값을 자동 맵핑하며 즉각 반영한다.
- setState()가 컴포넌트를 항상 즉각적으로 갱신하는 명령이 아니다. '갱신 요청'으로 생각하면 편하다. setState()를 사용해도 다른 변경 사항들과 한꺼번에 갱신하기 위해 갱신 타이밍이 뒤로 미뤄질 수 있다는 걸 주의하자.
참고 자료
'Frontend > React' 카테고리의 다른 글
| 리액트의 이벤트 처리 방식 까보기 (0) | 2025.03.11 |
|---|---|
| [react] 달력 만들기 01 (0) | 2023.01.31 |
| [HOC] about HOC(Higher Order Component) (0) | 2022.09.13 |
| [Redux Tutorial] Login page 만들며 Redux 이해하기 (0) | 2022.09.13 |
| [Redux Tutorial] about Redux (0) | 2022.09.13 |