4 분 소요

enter image description here


📖 React class vs function style

class 스타일과 함수 스타일이 대등하게 비교할수 있는 이유는 비교적 최신 기능으로 등장한 hook이라는 기능 덕분입니다.

과거의 함수 스타일에는 state값을 가질수가 없었습니다. 그리고 component가 생성되고 업데이트되고 소멸되는 과정인 component life cycle과정을 처리할수가 없었습니다.

hook의 등장으로 함수 스타일에서도 state와 life cycle을 관리할수 있게 되었습니다.


비교

function 방식으로 컴포넌트를 만들때에는 return을 하면 됩니다. class 방식은 render라는 이름의 함수, 즉 메소드를 정의해서 return 값이 ui가 되는 방식입니다. 즉 class 방식은 render라는 함수, 함수 방식은 자기 자신이 render함수 입니다.

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

function App() {
  return (
    <div className="container">
      <h1>hello world</h1>
      <FuncComp></FuncComp>
      <ClassComp></ClassComp>
    </div>
  );
}

function FuncComp() {
  return (
    <div className="container">
      <h2>function style component</h2>
    </div>
  );
}

class ClassComp extends React.Component {
  render() {
    return (
      <div className="container">
        <h2>class style component</h2>
      </div>
    );
  }
}

export default App;

class, function 에서 state 사용법

과거에는 class 방식에서만 사용이 가능했습니다. 하지만 최근에는 function 에서도 사용이 가능해졌습니다.

  • ✔ class 방식으로 state를 사용해보겠습니다.

    버튼을 누르면 ‘Number :’ 에 렌덤 숫자 값을 출력해주는 버튼을 만들어 보겠습니다. 처음 해야할 일은 초기값이 필요합니다. state를 정할때 number 라는 state값을 주겠습니다. 이대 props를 통해 전달된 initNumber 값을 전달하면 initNumber를 통해 전달된 값이 number에 저장됩니다. 즉 state는 number의 값이 2가 되었습니다. {this.state.number}를 입력하면 ‘‘Number : 2’ 라고 출력됩니다. state값을 바꿀 때마다 render 메소드가 호출되면서 달라진 state값이 시각적인 요소에 반영이 됩니다. 그 작업을 하기위해서 렌덤값을 만드는 버튼을 만들었습니다. this.setState를 통해서 state값을 바꾸어 줍니다. state값이 바뀌면 render 메소드가 호출되면서 바뀐 결과가 반영됩니다.

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

function App() {
  return (
    <div className="container">
      <h1>hello world</h1>
      <ClassComp initNumber={2}></ClassComp>
    </div>
  );
}

class ClassComp extends React.Component {
  state = {
    number: this.props.initNumber,
  };
  render() {
    return (
      <div className="container">
        <h2>class style component</h2>
        <p>Number : {this.state.number}</p>
        <input
          type="button"
          value="random"
          onClick={function () {
            this.setState({ number: Math.random() });
          }.bind(this)}
        />
      </div>
    );
  }
}

export default App;
  • ✔ function 방식으로 state를 사용해보겠습니다.

    리액트의 공식 문서를 보면 react 16.8 버전에 Hook 이라는 기능이 추가되었습니다. 먼저 함수에서 state를 사용하기 위해서는 useState라는 Hook을 사용해야합니다. 방법은 import React, { useState } from "react"; 입니다. useState 를 console.log를 통해 무엇있지 확인해 보겠습니다. useState는 2개의 값으로 이루어저 이는 배열입니다. 즉 useState를 사용하면 2개의 값이 있는 배열을 리턴합니다. 첫번째 값은 우리가 원하는 state 값이 될것입니다. 다음 class 방식에서 보면 state의 초기값으로 this.props.initNumber 를 주었습니다. 여기서 initNumber 라면 props를 통해 전달해주었던 값입니다. <ClassComp initNumber={2}></ClassComp>; 즉 2 입니다. function 방식에서는 useState의 첫번째 인자로 값을 넘겨줍니다. ` useState(props.initNumber) 만약 useState에 props.initNumber가 아닌 숫자중 하나인 7을 입력하면 초기값은 7이 됩니다. 위의 class 방식에서 렌덤 번호 생성 버튼을 누르면 Number의 값이 바뀝니다. 그 이유는 this.setState()에 새로운 state값을 넘겨줌으로써 state를 업데이트 시키고 react가 class의 render() 메소드를 호출한다. 라는 순서입니다.

    이 순서를 함수 방식에서는 useState의 2번재 값이 상태를 바꾸는 함수입니다. 위의 class 방식의 렌덤 번호 생성 버튼과 함수 방식의 버튼과 비교해서 보시면됩니다. 함수 방식에서 state를 만들때에는 react의 useState를 호출합니다. 인자로는 그 state의 초기 값을 넣어줍니다. useState는 2개값으로 되어있는 배열을 리턴합니다. 첫번째로는 상태값입니다 즉 초기 값입니다. 두번째 값은 그 상태를 바꿀수 있는 함수입니다. 우리는 첫번째 값과 두번째 값을 통해서 함수 안에서의 state를 사용할수 있게 되는것입니다.

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

function App() {
  return (
    <div className="container">
      <h1>hello world</h1>
      <FuncComp initNumber={2}></FuncComp>
    </div>
  );
}

function FuncComp(props) {
  const numberState = useState(props.initNumber);
  const number = numberState[0];
  const setNumber = numberState[1];

  console.log("numberState", numberState);

  return (
    <div className="container">
      <h2>function style component</h2>
      <p>Number : {number}</p>
      <input
        type="button"
        value="random"
        onClick={function () {
          setNumber(Math.random());
        }}
      />
    </div>
  );
}

export default App;

예제

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

function App() {
  return (
    <div className="container">
      <h1>hello world</h1>
      <FuncComp initNumber={2}></FuncComp>
      <ClassComp initNumber={2}></ClassComp>
    </div>
  );
}

function FuncComp(props) {
  const numberState = useState(props.initNumber);
  const number = numberState[0];
  const setNumber = numberState[1];

  const dateState = useState(new Date().toString());
  const _date = dateState[0];
  const setDate = dateState[1];

  return (
    <div className="container">
      <h2>function style component</h2>
      <p>Number : {number}</p>
      <input
        type="button"
        value="random"
        onClick={function () {
          setNumber(Math.random());
        }}
      />
      <p>date : {_date}</p>
      <input
        type="button"
        value="date"
        onClick={function () {
          setDate(new Date().toString());
        }}
      />
    </div>
  );
}

class ClassComp extends React.Component {
  state = {
    number: this.props.initNumber,
    _date: new Date().toString(),
  };
  render() {
    return (
      <div className="container">
        <h2>class style component</h2>
        <p>Number : {this.state.number}</p>
        <input
          type="button"
          value="random"
          onClick={function () {
            this.setState({ number: Math.random() });
          }.bind(this)}
        />
        <p>Date : {this.state._date}</p>
        <input
          type="button"
          value="date"
          onClick={function () {
            this.setState({ _date: new Date().toString() });
          }.bind(this)}
        />
      </div>
    );
  }
}

export default App;

📌function 방식 useState 축약형

주석처리된 3줄의 코드를 ` const [_date, setDate] = useState(new Date().toString() 과 같이 축약형으로 사용할수 있습니다.

function FuncComp(props) {
  const numberState = useState(props.initNumber);
  const number = numberState[0];
  const setNumber = numberState[1];

  // const dateState = useState(new Date().toString());
  // const _date = dateState[0];
  // const setDate = dateState[1];

  const [_date, setDate] = useState(new Date().toString());

  return (
    <div className="container">
      <h2>function style component</h2>
      <p>Number : {number}</p>
      <input
        type="button"
        value="random"
        onClick={function () {
          setNumber(Math.random());
        }}
      />
      <p>date : {_date}</p>
      <input
        type="button"
        value="date"
        onClick={function () {
          setDate(new Date().toString());
        }}
      />
    </div>
  );
}

댓글남기기