state는 Toggle Switch나 Counter처럼 컴포넌트 내부에서 변할 수 있는 값이라고 했다. 실제 애플리케이션에서는 무엇이 '상태'라고 할 수 있을까?
쇼핑몰 장바구니를 예로 들어보면, 사용자는 구매할 물건과 당장은 구매하지 않을 물건을 체크박스에 체크하여 구분 짓는다. 이를 장바구니 내에서의 상태로 구분해 본다면 check 된 상태
와 check 되지 않은 상태
이다.
체크박스를 코드로 구현해 보면 아래와 같다. 아래 예시에서는 단순히 체크된 상태에 따라 보이는 글시가 달라지지만, 이를 쇼핑몰에 적용하면 체크 여부에 따라 구매할 물건의 개수나 구매 금액이 변경되고, 이에 따라 사용자의 화면 또한 달라진다. 이처럼 컴포넌트 내에서 변할 수 있는 값,즉 상태는 React state로 다뤄야 한다.
import React, { useState } from "react";
import "./styles.css";
function CheckboxExample() {
const [isChecked, setIsChecked] = useState(false);
const handleChecked = (event) => {
setIsChecked(event.target.checked);
};
return (
<div className="App">
<input type="checkbox" checked={isChecked} onChange={handleChecked} />
<span>{isChecked ? "Checked!!" : "Unchecked"}</span>
</div>
);
}
export default CheckboxExample;
React에서는 state를 다루는 방법 중 하나로 useState
라는 특별한 함수를 제공한다. 이 함수의 사용 방법과 작동 방식을 위의 체크박스 예로 들어 보겠다.
useState
를 이용하기 위해서는 React로 부터 useState
를 불러와야 한다. import
키워드로 useState
를 불러오자. import{ useState} from "react";
useState
를 컴포넌트 안에서 호출해준다. useState
를 호출한다는 것은 "state"
라는 변수를 선언하는 것과 같으며, 이 변수의 이름은 아무 이름으로 지어도 된다. 일반적인 변수는 함수가 끝날 때 사라지지만, state변수는 react에 의해 함수가 끝나도 사라지지 않는다.isChecked
,setIsChecked
는 useState
의 리턴값을 구조분해 할당한 변수이다.function CheckboxExample(){
// 새로운 state 변수를 선언하고, 여기서는 이걸 isChecked라 부른다.
const[isChecked, setIsChecked] = useState(false);
}
function CheckboxExample(){
//1번 코드를 풀어쓰면,
const[isChecked, setIsChecked] = useState(false); //1번
// ...
// 2번 코드와 같다.
const stateHookArray = useState(false);
const isChecked = stateHookArray[0];
const steIsChecked = stateHookArray[1];
}
useState
를 호출하면 배열을 반환하는데, 배열의 0번째 요소는 현재 state 변수이고, 1번째 요소는 이 변수를 갱신할 수 있는 함수이다. useState
의 인자로 넘겨주는 값은 state의 초깃값이다.const [state 저장 변수, state 갱신 함수] = useState(상태 초기 값);
isChecked
: state를 저장하는 변수setIsChecked
" state isChecked
를 변경하는 함수 useState
: state hookfalse
: state 초깃값function CheckboxExample(){
const[isChecked, setIsChecked] = useState(false);
//const [state 저장 변수, state 갱신 함수] = useState(상태 초기 값)
}
isChecked
가 boolean 값을 가지기 때문에 true
or false
여부에 따라 다른 결과가 보이도록 삼항연산자를 사용한다.<span>{isChecked ? "Checked!!" : "Unchecked"}</span>
state를 갱신하려면 state 변수를 갱신할 수 있는 함수인 setIsChecked
를 호출한다.
이번 예시의 경우, input[type = checkbox]
JSX 엘리먼트의 값 변경에 따라서 isChecked
도 변경되어야 한다.
input[type=checkbox]
엘리먼트의 값이 변경되면 onChange
이벤트가 발생하고, 이벤트 핸들러 함수가 작동되는 패턴을 DOM을 다뤄보면 익숙해질 것이다. 유효성 검사 스프린트에서 input[type = text]
엘리먼트의 값이 변경될 때, 이벤트 핸들러 함수를 작동시키는 패턴을 복습해 보자.
React도 마찬가지. 사용자가 체크박스 값을 변경하면 onChange
이벤트가 이벤트 핸들러 함수인 handleChecked
를 호출하고, 이 함수가 setIsChecked
를 호출하게 된다. setIsChecked
가 호출되면 호출된 결과에 따라 ischecked
변수가 갱신되며, React는 새로운 isChecked
변수를 CheckboxExample
컴포넌트에 넘겨 해당 컴포넌트를 다시 렌더링 한다.
function CheckboxExample() {
const [isChecked, setIsChecked] = useState(false);
const handleChecked = (event) => {
setIsChecked(event.target.checked);
};
return (
<div className="App">
<input type="checkbox" checked={isChecked} onChange={handleChecked} />
<span>{isChecked ? "Checked!!" : "Unchecked"}</span>
</div>
);
}
지금까지 state hook 사용법에 대해서 학습했다.
state hook 사용시 주의점에 대해서도 알아보자
"rerendered?"
가 찍히는 것을 확인할 수 있다. 즉, 컴포넌트의 상태가 변경될 때마다 새롭게 호출되고, 리렌더링 된다.import React, { useState } from "react";
import "./styles.css";
function CheckboxExample() {
console.log("rerendered?");
const [isChecked, setIsChecked] = useState(false);
const handleChecked = (event) => {
setIsChecked(event.target.checked);
};
return (
<div className="App">
<input type="checkbox" checked={isChecked} onChange={handleChecked} />
<span>{isChecked ? "Checked!!" : "Unchecked"}</span>
</div>
);
}
export default CheckboxExample;
state.push(1);
, state[1]=2;
, state='wrong state';