본문 바로가기
Frontend/React

[React] 클래스, 함수형 컴포넌트 생명주기(Lifecycle)와 생명주기 함수(Hook)

by 디스코비스킷 2025. 4. 10.
반응형

컴포넌트의 생명주기는 React 애플리케이션에서 컴포넌트가 생성되고 업데이트되며 사라지는 과정을 의미한다. 

먼저, 컴포넌트의 생명주기는 크게 3단계로 나뉜다.

  1. Mount(화면에 그려짐): 컴포넌트가 생성될 때.
  2. Update(화면 업데이트): 컴포넌트의 props가 변경되거나 setState()함수 호출에 의해 state가 변경되거나, forceUpdate()라는 강제 업데이트 함수 호출로 인해 컴포넌트가 다시 렌더링 될 때.
  3. Unmount(화면에서 사라짐): 상위컴포넌트에서 현재 컴포넌트를 더 이상 화면에 표시하지 않게 될 때. 

 

생명주기 함수는 이 일련의 과정 속에서 특정 시점에 자동으로 호출되는 함수를 말한다. 생명주기 함수들을 사용하면 컴포넌트가 렌더링되기 전이나 후, 상태나 props가 변경될 때, 컴포넌트가 사라지기 직전 등의 시점에 데이터 요청, 이벤트 등록, 정리(clean-up) 등의 작업을 수행할 수 있다. 

 

클래스형과 함수형 컴포넌트는 생명주기를 관리하는 방식이 다른데, 이를 비교해보며 잘 숙지해보도록 하자!

1. 클래스형 컴포넌트 생명주기

클래스형 컴포넌트의 생명주기와 생명주기 함수에 대한 설명은 위와 같다. 

componentDidMount()

  • 언제 실행되는가: 컴포넌트가 처음 마운트된 직후 1회 실행됨.
  • 주 용도: API 요청, 이벤트 리스너 등록, 타이머 설정 등 최초 초기화 작업.

componentDidUpdate(prevProps, prevState)

  • 언제 실행되는가: 업데이트(리렌더링) 직후 실행됨. props나 state가 변경되었을 때.
  • 주 용도: 이전 상태와 비교하여 조건부 로직 실행 시 사용.

componentWillUnmount()

  • 언제 실행되는가: 컴포넌트가 DOM에서 제거되기 직전 실행됨.
  • 주 용도: 타이머 해제, 이벤트 리스너 제거, 정리 작업 등.
class MyComponent extends Component {
  state = { count: 0 };

  componentDidMount() {
    console.log('마운트됨');
  }

  componentDidUpdate() {
    console.log('업데이트됨');
  }

  componentWillUnmount() {
    console.log('곧 언마운트됨');
  }

  handleClick = () => {
    this.setState({ count: this.state.count + 1 });
  };

  render() {
  	console.log('렌더링됨');
    return (
      <div>
        <p>카운트: {this.state.count}</p>
        <button onClick={this.handleClick}>+1</button>
      </div>
    );
  }
}

2. 함수형 컴포넌트 생명주기

함수형 컴포넌트는 useEffect 훅을 이용하여 클래스형 생명주기와 동일한 기능을 수행한다. Hook이란 갈고리인데, 함수형 컴포넌트에 상태 관리나 생명주기와 같은 기능을 '걸어' 사용할 수 있도록 도와준다. 이를 통해 클래스형 컴포넌트 없이도 상태와 사이드 이펙트를 다룰 수 있다.

useEffect의 실행 시점

형태 실행 시점 설명
useEffect(() => {}) 매 렌더링마다 실행됨 (마운트 + 업데이트 모두)
useEffect(() => {}, []) 처음 마운트 시 1회 실행됨 (클래스형의 componentDidMount와 유사)
useEffect(() => {}, [dep]) dep 값이 바뀔 때만 실행 (클래스형의 componentDidUpdate와 유사)

마운트, 언마운트, 상태값 변화 대응

  • 마운트: useEffect(() => {}, [])
  • 언마운트: useEffect의 return 함수
  • 특정 상태값 변화 감지: useEffect(() => { ... }, [특정 상태])
useEffect(() => {
  console.log("마운트될때 한번 실행");
}, []);


useEffect(() => {
  console.log("count값이 변경될 때마다 실행됨");

  return () => {
    console.log("언마운트 또는 다음 실행 전 클린업");
  };
}, [count]);

의존성 배열이란?

  • useEffect의 두 번째 인자로 전달되는 배열이다.
  • 이 배열에 명시된 값이 변할 때만 해당 useEffect가 재실행됨.
  • 배열이 비어 있으면 한 번만 실행됨.

3. React 생명주기 함수의 필요성

React에서 생명주기를 관리하는 이유는 컴포넌트의 수명 주기마다 특정 작업을 안전하게 처리하기 위해서다.

서버에서 데이터를 받아오는 경우

  • 마운트 시 API 요청 → componentDidMount / useEffect(() => {}, [])
  useEffect(() => {
    try {
      const response = await axios.get(url);
      // console.log(response.data);
      const pokemonData = formatPokeData(response.data);
      setPokemon(pokemonData);
    } catch (error) {
      console.error(error);
    }
  }, []);

이벤트 핸들러를 사용하는 경우

  • 등록 시점과 해제 시점을 명확히 하기 위해 필요 → componentDidMount / componentWillUnmount
useEffect(() => {
  window.addEventListener("resize", handleResize);
  return () => {
    window.removeEventListener("resize", handleResize);
  };
}, []);

타이머 함수 사용하는 경우

  • setInterval 또는 setTimeout 등의 등록/해제를 정확히 제어
useEffect(() => {
  const timer = setInterval(() => {
    console.log("1초마다 실행");
  }, 1000);

  return () => {
    clearInterval(timer); // 컴포넌트 언마운트 시 제거
  };
}, []);

클린업(Cleanup) 함수란?

위 예시코드에서 clearInterver(timer)을 담아 리턴되는 함수를 보면된다.

  • useEffect에서 리턴되는 함수
  • 컴포넌트가 언마운트되거나, 의존성 배열이 바뀌기 전에 실행됨
  • 주로 이벤트 리스너 제거, 타이머 해제 등에 사용
반응형

최근댓글

최근글

© Copyright 2024 ttutta