Function Component | Class Component |
---|---|
state 사용 불가 | 생성자에서 state를 정의 |
Lifecycle에 따른 기능 구현 불가 | setState() 함수를 통해 state업데이트 |
Hooks | Lifecycle methods 제공 |
const [변수명, set함수명] = useState(초기값);
import React, { useState } from "react";
function Counter(props) {
const [count, setCount] = useState(0);
return (
<div>
<p>총 {count}번 클릭했습니다.<p>
<button onClick={() => setCount(count + 1)}>
클릭
</button>
</div>
);
}
useEffect(이펙트 함수, 의존성 배열);
useEffect(이펙트 함수, [ ]); → mount, unmount시 단 한번씩만 실행
useEffect(이펙트 함수); → 컴포넌트가 업데이트 될 때마다 호출
componentDidMonut, componentDidUpdate를 사용한 예제
import React, { useState, useEffect } from "react";
function Counter(props) {
const [count, setCount] = useState(0);
useEffect(() => {
// 브라우저 api를 사용해서 document의 title을 업데이트 함
document.title = `You clicked ${count} times`;
});
return (
<div>
<p>총 {count}번 클릭했습니다.<p>
<button onClick={() => setCount(count + 1)}>
클릭
</button>
</div>
);
}
componentWillUnmonut를 사용한 예제
import React, { useState, useEffect } from "react";
function UserStatus(props) {
const [isOnline, setIsOnline] = useState(null);
function handleStatusChange(status) {
setIsOnline(status.isOnline);
}
useEffect(() => {
ServerAPI.subscribeUserStatus(props.user.id, handleStatusChange);
// 컴포넌트가 unmount될 때 호출됨
return () => {
ServerAPI.unsubscribeUserStatus(props.user.id, handleStatusChange);
};
});
if (isOnline === null) {
return '대기 중...';
}
return isOnline ? '온라인' : '오프라인';
}
하나의 컴포넌트에 2개의 useEffect를 사용한 예제
import React, { useState, useEffect } from "react";
function UserStatusWithCounter(props) {
const [count, setCount] = useState(0);
useEffect(() => {
document.title = `총 ${count}번 클릭했습니다.`;
});
const [isOnline, setIsOnline] = useState(null);
useEffect(() => {
ServerAPI.subscribeUserStatus(props.user.id, handleStatusChange);
return () => {
ServerAPI.unsubscribeUserStatus(props.user.id, handleStatusChange);
};
});
function handleStatusChange(status) {
setInOnline(status.isOnline);
}
useEffect(() => {
// 컴포넌트가 마운트 된 이후,
// 의존성 배열에 있는 변수들 중 하나라도 값이 변경되었을 때 실행
// 의존성 배열에 빈 배열[]을 넣으면 마운트와 언마운트시에 단 한 번씩만 실행됨
// 의존성 배열 생략 시 컴포넌트 업데이트 시마다 실행됨
...
return () => {
// 컴포넌트가 마운트 해제되기 전 실행됨
}
}, [의존성 변수1, 의존성 변수2, ...]);
const memoizedVulue = useMemo(
() => {
// 연산량이 높은 작업을 수행하여 결과를 반환
return computeExpensiveValue(의존성 변수1, 의존성 변수2);
},
[의존성 변수1, 의존성 변수2]
);
// 의존성 배열을 넣지 않을 경우, 매 렌더링마다 함수가 실행 됨
const memoizedVulue = useMemo(
() => computeExpensiveValue(a,b)
);
// 의존성 배열이 빈 배열일 경우, 컴포넌트 마운트 시에만 호출 됨
const memoizedVulue = useMemo(
() => {
return computeExpensiveValue(a,b);
},
[]
);
const memoizedVulue = useCallback(
() => {
doSomething(의존성 변수1, 의존성 변수2);
},
[의존성 변수1, 의존성 변수2]
);
const refContainer = useRef(초기값);
function TextInputWithFocusButton(props) {
const inputElem = useRef(null);
const onButtonClick = () => {
// `current`는 마운트된 input element를 가리킴
inputElem.current.focus();
};
return (
<>
<input ref={inputElem} type="text" />
<button onClick={onButtonClick}>
Focus the input
</button>
</>
);
}