컴포넌트 생명주기 단계

Muru·2024년 7월 26일

[React] 지식 저장소

목록 보기
3/30
post-thumbnail

1. 컴포넌트 생명 주기

컴포넌트에도 생명주기가 있다.

생성 => 업데이트 => 제거 의 단계를 거치게 되는데

클래스형 컴포넌트에서는 이러한 단계를 생명주기 메소드를 사용하여 설명할 수 있다.

  1. 생성(Mounting) : 컴포넌트가 처음 DOM에 삽입할때 발생한다
    constructor()
    static getDerivedStateFromProps()
    render()
    componentDidMount() : 렌더링 된 이후에 실행이되는 함수

  2. 업데이트(Updating) : 컴포넌트의 props나 state가 변경될때 발생한다.
    우리가 흔히 하는 "리렌더링"과정은 해당 업데이트 단계에서 발생한다.
    static getDerivedStateFromProps()
    shouldComponentUpdate()
    render()
    getSnapshotBeforeUpdate()
    componentDidUpdate()

  3. 삭제(Unmounting) : 컴포넌트가 DOM에서 제거하려할때 발생.
    관련 메소드는 한개다.
    componentWillUnmount() : DOM에서 제거하기 전에 해당 메소드가 실행되고나서야 컴포넌트가 언마운트된다.

다음 코드 App.js 와 MyComponent.js를 가지고 이해해보자.
import React from 'react';
import ReactDOM from 'react-dom';
import MyComponent from './MyComponent';

App.js

class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = { showComponent: true, count: 0 };
    console.log('App constructor');
  }

  toggleComponent = () => {
    this.setState(state => ({ showComponent: !state.showComponent }));
  }

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

  componentDidMount() {
    console.log('App componentDidMount : 컴포넌트가 마운트 된 후에 한번 실행됨 렌더링직후');
  }

  render() {
    console.log('App render');
    return (
      <div>
        <button onClick={this.toggleComponent}>
          Toggle Component
        </button>
        <button onClick={this.increment}>
          Increment
        </button>
        {this.state.showComponent && <MyComponent />}
        <div>
          <h1>Count: {this.state.count}</h1>
        </div>
      </div>
    );
  }
}

export default App;

MyComponent.js

import React from 'react';

class MyComponent extends React.Component {
  constructor(props) {
    super(props);
    console.log('MyComponent constructor');
    this.state = {};
  }

  componentDidMount() {
    console.log('MyComponent componentDidMount : 컴포넌트가 마운트 된 후에 한번 실행됨 렌더링 직후' );
  }

  componentWillUnmount() {
    console.log('MyComponent componentWillUnmount : 컴포넌트가 언마운트되기전 실행됨');
  }

  render() {
    console.log('MyComponent render');
    return (
      <div>
        MyComponent is mounted with count: {this.props.count}
      </div>
    );
  }
}

export default MyComponent;


컴포넌트의 생명주기에 맞게 적절하게 코드가 실행이 되었다.

increment 버튼을 눌러보자.


State의 변화만 이루어졌으므로 업데이트의 단계에 속한다.
이때 마운트 단계는 안거치고 리렌더링만 되다는것을 유의하자.
당연하게도 App 컴포넌트가 리렌더링이 되었으므로 MyComponent 컴포넌트도 따라서 리렌더링이 된다. 해당 컴포넌트 역시 업데이트일 뿐이므로 마운트 단계는 안거친다.



다음으로 Toogle componet 버튼을 클릭하여 컴포넌트를 DOM상에서 없애보자.


가장먼저 App 컴포넌트에서 상태변화 MyComponent의 출력 = false로 바뀌므로 리렌더링이 된다. 이때 MyComponent의 컴포넌트는 언마운트 되므로 언마운트되기전 실행되는 함수 componentWillunmount 함수가 실행되는것을 볼 수 있다.



요즘 추세는 클래스형 컴포넌트들보다는 함수형 컴포넌트를 많이사용하는 추세다. 즉 위 클래스형 메소드들은 함수형 컴포넌트에서 사용하지 못한다.
하지만 UseEffect() , useMemo() , useState() 등의 Hook의 등장으로 클래스형 컴포넌트의 메소드들을 대체할 수 있게끔 사용이 가능해진다.

2. 함수형 컴포넌트에서 클래스형 메소드 사용

위에서도 설명했지만 클래스형 메소드를 훅으로 대체하여 거의 비슷하게 사용할 수 있다.



간략하게 대표적으로 어떻게 매칭할 수 있는지 알아보자.
왼쪽에서는 클래스형 메소드함수명을 적고
오른쪽 설명에서는 함수형 컴포넌트에서는 우리가 보통 어떻게 쓰고있는지를 말한다.

  1. 생성(Mount)
    constructor: 훅에서는 useState를 사용하여 상태를 초기화 할 수 있다.
    render: 함수형 컴포넌트의 반환 값 (return문)이 곧 JSX다.
    componentDidMount: 훅에서는 useEffect를 빈 배열을 의존성으로 사용하여 마운트 시 한 번만 실행되게 한다.

  2. 업데이트(Update)
    shouldComponentUpdate : React.memo를 사용하여 컴포넌트 리렌더링을 제어할 수 있다.

  3. 삭제(unmount)
    componentWillUnmount: 훅에서는 useEffect의 cleanup 함수를 사용하여 컴포넌트가 언마운트되기 직전에 실행된다.

3. 마운트 vs 렌더링

번외로 마운트와 렌더링의 차이점을 간략하게 말하면

마운트는 컴포넌트가 처음 DOM에 추가되는 과정으로 컴포넌트가 처음 생성할때 한번만 실행이되는 과정이다.

렌더링은 컴포넌트가 화면에 어떻게 표시할것인가를 결정하고 그 결과를 DOM에 반영하는 과정이다.
Props나 state 변경시 여러 번 발생 할 수 있다

profile
Developer

0개의 댓글