본문 바로가기

학습노트/React

[React Hook] React Hooks란?, Lifecycle의 개념

React Hooks란?

  간단하게 설명하자면 기존 React의 Class 활용한 Component 설정 방법을 개선한 것이다. 기존의 단점은 세 가지 정도로 꼽을 수 있다.


1. 계층이 너무 많아진다.

 

2. Component가 너무 복잡해진다.

 

3. Class를 Component로 쓰면 bind, this를 쓰는데 이 방식은 컴퓨터에게는 복잡한 작업을 수행하게 하고 사람에게는 혼란을 발생시킨다.


 

  위 세 가지 단점을 종합해서 말하자면 가독성이 떨어진다고 할 수 있다. 따라서 react hook은 Class 형태였던 Component를 function을 통해 만들 수 있게 해주는 API이다.

 

  React Hook를 사용할 때에는 실질적으로 두 가지만 사용한다. useState()와 useEffect()가 바로 그것이다. useState는 state관리에 사용되어지고 useEffect는 lifecycle관리에 사용되어진다.

 


즉, React Hooks를 사용하게 되면 코드의 가독성이 좋아지고 component의 재사용성이 간편해진다.

 



Lifecycle이란?

  프로그래밍에서 Lifecycle은 어떤 애플리케이션이 실행되고 종료되는 과정을 의미한다. 특히 React에서는 애플리케이션의 실행부터 종료까지 과정을 세밀하게 나누어서 컨트롤할 수 있습니다.

 

 

 

 


Class 기반 lifecycle

  아래 코드처럼 실행을 해보면 개발자도구 console창에 constructor -> will mount -> render -> Did mount 이런 식으로 lifecycle에 순서에 맞게 코드가 진행되는 것을 볼 수 있다.

import React, { Component } from 'react';
import './App.css';

class App extends React.Component {
  constructor() {
    super();
    console.log("constructor");
  }
  componentWillMount() {
    console.log("will mount!");
  }
  componentDidMount() {
    console.log("Did mount!");
  }
  render() {
    console.log("render");
    return (
      <div>
        <h1>ukcasso
        </h1>
      </div>
    );
  }
}

export default App;

 


Hooks 기반 lifecycle

  react의 useEffect는 componentDidMount와 componentDidUpdate, componentWillUnmount가 합쳐진 것이라고 생각하는 것이 좋다. 하지만 componentDidMount, componentDidUpdate와는 달리 effect는 브라우저가 화면을 업데이트하는 것을 차단하지 않는다. 때문에 더 향상된 반응성을 보여준다.  useEffect는 비동기시에 사용하고 동기적인 실행을 하기 위해서는 useEffect와 동일한 API를 사용하는 useLayoutEffect를 사용하면 된다.

 

  아래에 예시가 있다. Clicked me버튼을 클릭하면 h2태그의 state변수가 증가하는 간단한 예시이다. 이런식으로 코드를 작성하게 되면 react component가 마운트 된 이후에 console.log가 보여지기 때문에 componentDidMount역할을 한다고 볼 수 있다.

import './App.css';
import React, { useState, useEffect } from "react";

export const App = () => {
  const [count, setCount] = useState(0);

  // componentDidMount, componentDidUpdate와 같은 방식으로
  useEffect(() => {
    // 브라우저 API를 이용하여 업데이트 합니다.
    console.log("component did mount with useEffect!");
  });
  return (
    <div>
      <h2>You clicked {count} times.</h2>
      <button onClick={() => {setCount(count + 1)}}>
        Click me
      </button>
    </div>
  );
};

export default App;

 

  그리고 이런 식으로 코드를 []추가하면 state가 변화되더라도 component를 re-render하지 않겠다는 의미여서 버튼을 계속눌러도 state는 변하지만 console.log는 찍히지 않는다. 그 뜻은 render가 되지 않았기 때문에 mount되지 않는다는 말이다.

  useEffect(() => {
    console.log("component did mount with useEffect!");
  },[]);

 

 

  이번엔 []안에 count를 넣는다. 그것은 count라는 state가 변경될시에 component를 re-render하겠다는 의미이다.

  useEffect(() => {
    console.log("component did mount with useEffect!");
  },[count]);

 

 

  다음엔 componentWillIUnmount를 볼 수 있는 코드인데 component가 이제 사라질 때 어떤 행동을 하는 것을 의미하는 것이다. 그것은 return으로 설정해주면 된다.

import './App.css';
import React, { useState, useEffect } from "react";

export const App = () => {
  const [count, setCount] = useState(0);

  // componentDidMount, componentDidUpdate와 같은 방식으로
  useEffect(() => {
    // 브라우저 API를 이용하여 업데이트 합니다.
    console.log("component did mount with useEffect!");
    return () => {
     console.log("component is finished")
    }
  }, [count]);
  return (
    <div>
      <h2>You clicked {count} times.</h2>
      <button onClick={() => {setCount(count + 1)}}>
        Click me
      </button>
    </div>
  );
};

export default App;