๐Ÿ’ป๐Ÿ’€/๊ฐœ๋ฐœ

[React] ์ปดํฌ๋„ŒํŠธ ๊ฐ•์ œ Re-renderํ•˜๊ธฐ (re-render ์›๋ฆฌ์— ๋Œ€ํ•œ ์ดํ•ด)

db2 2021. 9. 12. 10:28

์›๊ธ€: How and when to force a React component to re-render (์ฃผ์˜โ• ์˜์—ญ ๋‹ค์ˆ˜ ์กด์žฌ)

https://javascript.plainenglish.io/re-render-a-functional-react-component-1d64fa9a0c60

๋ฆฌ์•กํŠธ๋Š” ๋ณดํ†ต ์ž๋™์ ์œผ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฆฌ๋ Œ๋”ํ•œ๋‹ค. ํ•˜์ง€๋งŒ ๊ฐ•์ œ์ ์œผ๋กœ ๋ฆฌ์•กํŠธ๊ฐ€ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฆฌ๋ Œ๋”ํ•˜๋„๋ก ํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ๋ฆฌ์•กํŠธ์˜ ๋ฆฌ๋ Œ๋” ๋ฐฉ์‹์— ๋Œ€ํ•œ ์ดํ•ด๊ฐ€ ํ•„์š”ํ•˜๋‹ค.

์›น ๋ฐœ์ „์˜ ์‹œ์ž‘์—์„œ๋ถ€ํ„ฐ ์ง€๊ธˆ๊นŒ์ง€ HTML๊ณผ CSS๊ฐ€ ์›น ์‚ฌ์ดํŠธ์˜ ์‹œ๊ฐ์ ์ธ ๋ถ€๋ถ„์„ ๋‹ด๋‹นํ•˜๊ณ  ์žˆ๋‹ค. ํ•˜์ง€๋งŒ JavaScript๊ฐ€ ๋“ฑ์žฅํ•จ์œผ๋กœ์จ ์šฐ๋ฆฌ๋Š” ๋ Œ๋”๋ง๋œ ํŽ˜์ด์ง€์˜ HTML์„ ์ฝ๊ณ  ์—…๋ฐ์ดํŠธํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋˜์—ˆ๋‹ค. ์ด๋ฅผ DOM API๋ผ๊ณ  ํ•œ๋‹ค.

jQuery์™€ ๊ฐ™์€ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋Š” ์ด๋Ÿฌํ•œ DOM API ์œ„์— ํ–ฅ์ƒ๋œ ๊ธฐ๋Šฅ๊ณผ ํ˜ธํ™˜์„ฑ์„ ๊ฐ€์ง„ ์ถ”์ƒ์ ์ธ ๊ฐœ๋…์˜ ๋ ˆ์ด์–ด๋ฅผ ์ œ๊ณตํ–ˆ๊ณ , ์ด๋ฅผ ํ†ตํ•ด ๊ฐœ๋ฐœ์ž๋“ค์ด ์‰ฝ๊ฒŒ ์›น ์–ดํ”Œ๋ฆฌ์ผ€์ด์…˜์„ ๊ตฌ์ถ•ํ•  ์ˆ˜ ์žˆ๊ฒŒ ๋˜์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์—„์ฒญ๋‚œ ์ธ๊ธฐ๋ฅผ ๋Œ์—ˆ๋‹ค. ํ•˜์ง€๋งŒ jQuery๋Š” ํ•œ๊ณ„๊ฐ€ ์žˆ์—ˆ๋‹ค. ๊ฐœ๋ฐœ์ž๋“ค์ด ๋™์ ์œผ๋กœ ๋กœ๋“œ๋œ ์ปจํ…์ธ ๋“ค์„ ๋‹ค๋ฃฐ ๋•Œ ์ƒ๊ธฐ๋Š” ๊ฒฐ์ •์ ์ธ ๋ฌธ์ œ๋“ค(JavaScript์˜ ์ƒํƒœ(๋ณ€์ˆ˜)๊ฐ€ ๋ฐ”๋€Œ๋Š” ๊ฒƒ์ด DOM(HTML)์— ์ฆ‰์‹œ ์˜ํ–ฅ์„ ๋ผ์น˜์ง€ ๋ชปํ•ด์„œ ๊ฒฐ๊ณผ์ ์œผ๋กœ ๋‘˜์˜ ์‹ฑํฌ๋ฅผ ๋งž์ถ”์ง€ ๋ชปํ•œ ๊ฒƒ)์„ ํ•ด๊ฒฐํ•˜์ง€ ๋ชปํ–ˆ๋‹ค.

๋ฐ˜๋ฉด์— React์™€ ๊ฐ™์€ ํ”„๋ ˆ์ž„์›Œํฌ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•  ์ˆ˜ ์žˆ๋‹ค. React๋Š” ์–ดํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์ƒํƒœ๋ฅผ ์œ ์ง€ํ•˜๊ธฐ ์œ„ํ•ด JavaScript์— ์˜์กดํ•œ๋‹ค. ํŽ˜์ด์ง€์˜ ๊ฐ ๊ฐ์ฒด์— ๋Œ€ํ•œ JavaScript์˜ ์ฐธ์กฐ๊ฐ’์„ ํฌํ•จํ•˜๋Š” ์ตœ์ƒ์œ„ ๋ถ€๋ชจ ๊ฐ์ฒด๋ฅผ Virtual DOM์ด๋ผ๊ณ  ๋ถ€๋ฅธ๋‹ค. ์ด ๊ฐ€์ƒ DOM์— ์ƒ๊ธฐ๋Š” ๋ณ€ํ™”๋ฅผ ์ž๋™์ ์œผ๋กœ ์‹ค์ œ DOM์— ๋ฐ˜์˜ํ•˜๋Š” ๊ฒƒ์ด React์˜ ๊ฐ€์žฅ ํฐ ๊ธฐ๋Šฅ์ด๋‹ค. ๊ทธ๋Ÿฌ๋ฉด ์šฐ๋ฆฌ๋Š” ์–ด๋–ป๊ฒŒ ๊ฐ€์ƒ DOM์„ ์—…๋ฐ์ดํŠธ ํ•  ์ˆ˜ ์žˆ์„๊นŒ? ์ด๋Š” ์ปดํฌ๋„ŒํŠธ์—์„œ state์™€ props๋ฅผ ๋‹ค๋ฃธ์œผ๋กœ์จ ๊ฐ€๋Šฅํ•˜๋‹ค.

๊ทธ๋Ÿฌ๋ฉด ์—ฌ๊ธฐ์„œ ํ•œ ๊ฐ€์ง€ ์˜๋ฌธ์ ์ด ์ƒ๊ธด๋‹ค. ๋งŒ์•ฝ ์˜ˆ์ƒํ•œ ๋Œ€๋กœ ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์—…๋ฐ์ดํŠธ ๋˜์ง€ ์•Š๋Š”๋‹ค๋ฉด ์–ด๋–ป๊ฒŒ ๋ ๊นŒ? ๊ทธ๋Ÿด ๋•Œ ๊ฐ•์ œ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ์—…๋ฐ์ดํŠธ ํ•  ์ˆ˜๋„ ์žˆ์„๊นŒ?

์ปดํฌ๋„ŒํŠธ๊ฐ€ ๋ฆฌ๋ Œ๋”๋ง ๋˜์ง€ ์•Š๋Š” ์ด์œ 

์ž๋™์ ์œผ๋กœ ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์—…๋ฐ์ดํŠธ ๋˜์ง€ ์•Š๋Š”๋‹ค๊ณ  ํ•ด์„œ ๊ฐ•์ œ์ ์œผ๋กœ ๋ฆฌ๋ Œ๋”๋ง์„ ํ•˜๋Š” ๊ฒƒ์€ ์ข‹์€ ๋ฐฉ๋ฒ•์ด ์•„๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ๋ฆฌ๋ Œ๋”๋ฅผ ๊ณ ๋ คํ•˜๊ธฐ ์ด์ „์—, ์ž‘์„ฑํ•œ ์ฝ”๋“œ๋ฅผ ๋ถ„์„ํ•˜๋Š” ๊ฒƒ์ด ๋จผ์ €์ด๋‹ค. React ๊ธฐ๋Šฅ์˜ ํ™œ์šฉ์€ ๊ฒฐ๊ตญ ๊ฐœ๋ฐœ์ž์˜ ์ฝ”๋“œ์— ๋‹ฌ๋ ค์žˆ๋‹ค.

1. state๋ฅผ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์—…๋ฐ์ดํŠธ ํ•˜์ง€ ์•Š์€ ๊ฒฝ์šฐ

์—ฌ๊ธฐ ์ด๋ฆ„ Juan์„ ๋ณด์—ฌ์ฃผ๋Š” ๊ฐ„๋‹จํ•œ ์•ฑ์ด ์žˆ๋‹ค.

๋ฒ„ํŠผ์„ ํด๋ฆญํ•˜๋ฉด changeUserName ํ•จ์ˆ˜๊ฐ€ ํŠธ๋ฆฌ๊ฑฐ ๋˜๋ฉด์„œ ์ด๋ฆ„์ด Peter๋กœ ๋ฐ”๋€Œ๋„๋ก ์„ค๊ณ„๋๋‹ค. ํ•˜์ง€๋งŒ ๋ฒ„ํŠผ์„ ํด๋ฆญํ•ด๋„ ์•„๋ฌด๋Ÿฐ ์ผ๋„ ์ผ์–ด๋‚˜์ง€ ์•Š์„ ๊ฒƒ์ด๋‹ค.

import { useState } from "react";

function App() {
  const [user, setUser] = useState({
    name: "Juan"
  });

  function changeUserName() {
    user.name = "Peter";
    setUser(user);
  }

  return (
    <div className="App">
      <p>User name: {user.name}</p>

      <button onClick={changeUserName}>Change user name</button>
    </div>
  );
}

React๋Š” ์ƒํƒœ๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ์–•์€ ๋น„๊ต ์ฆ‰, ์ฐธ์กฐ๊ฐ’ ๋น„๊ต๋ฅผ ํ†ตํ•ด ์ด์ „ ๊ฐ’๊ณผ ํ˜„์žฌ ๊ฐ’์ด ๊ฐ™์€ ๊ฐ์ฒด์ธ์ง€๋ฅผ ์ฒดํฌํ•œ๋‹ค. ์œ„์˜ ์˜ˆ์‹œ์—์„œ ๋ฆฌ๋ Œ๋”๋ง์ด ๋ฐœ์ƒํ•˜์ง€ ์•Š์€ ์ด์œ ๋Š” user ๊ฐ์ฒด์˜ name์ด๋ผ๋Š” ํ”„๋กœํผํ‹ฐ๋งŒ์„ ์—…๋ฐ์ดํŠธ ํ–ˆ์„ ๋ฟ, user๊ฐ€ ๊ฐ€๋ฆฌํ‚ค๋Š” ์ฐธ์กฐ๊ฐ’์ด ์—…๋ฐ์ดํŠธ ๋œ ๊ฒƒ์ด ์•„๋‹ˆ๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค. React๋Š” setUser๊ฐ€ ํ˜ธ์ถœ๋˜๊ธฐ ์ „๊ณผ ํ›„์˜ user๋ฅผ ๊ฐ™์€ ์ฃผ์†Œ๋ฅผ ๊ฐ–๋Š” ๋™์ผํ•œ ๊ฐ์ฒด๋กœ ํŒ๋‹จํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์–ด๋– ํ•œ ๋ณ€ํ™”๋„ ๊ฐ์ง€ํ•˜์ง€ ๋ชปํ•œ ๊ฒƒ์ด๋‹ค.

React์˜ ์ƒํƒœ๋Š” ๋ถˆ๋ณ€์„ฑ์ด ์œ ์ง€๋˜์–ด์•ผ ํ•œ๋‹ค. ์ƒํƒœ์˜ ์ž๋ฃŒํ˜•์ด ์ฐธ์กฐํ˜•์ด๋ผ๋ฉด ์™„์ „ํžˆ ์ƒˆ๋กœ์šด ์ฐธ์กฐ๊ฐ’์„ ๊ฐ–๋Š” ์ƒํƒœ๋กœ ์—…๋ฐ์ดํŠธ๋ฅผ ํ•ด์ค˜์•ผํ•˜์ง€ ์ด์ „์˜ ์ƒํƒœ๋ฅผ ์ง์ ‘ ๊ฑด๋“œ๋ ค์„œ ์ผ๋ถ€๋งŒ ๋ณ€๊ฒฝํ•ด์„œ๋Š” ์•ˆ๋œ๋‹ค.

๊ทธ๋ ‡๋‹ค๋ฉด ์œ„์˜ ์ฝ”๋“œ๋ฅผ ์–ด๋–ป๊ฒŒ ์ˆ˜์ •ํ•˜๋ฉด ์ข‹์„๊นŒ? ๋‹ค์Œ๊ณผ ๊ฐ™์ด ๋ณ€๊ฒฝ๋œ ๊ฐ’์„ ํฌํ•จํ•˜๋Š” ์ƒˆ๋กœ์šด ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•ด์„œ ์—…๋ฐ์ดํŠธ ํ•จ์ˆ˜์— ์ „๋‹ฌํ•˜๋ฉด ๋œ๋‹ค.

function changeUserName() {
   setUser({
     ...user,
     name: "Peter"
   });
}

๊ธฐ์กด ๊ฐ์ฒด์˜ ํ”„๋กœํผํ‹ฐ ๊ฐ’๋“ค์€ ์œ ์ง€ํ•˜๋ฉด์„œ name ํ”„๋กœํผํ‹ฐ๋งŒ ์—…๋ฐ์ดํŠธ ํ•˜๋˜, spread ์—ฐ์‚ฐ์ž๋ฅผ ์‚ฌ์šฉํ•ด์„œ ๊ฒฐ๊ณผ์ ์œผ๋กœ๋Š” ์ƒˆ๋กœ์šด ์ฐธ์กฐ๊ฐ’์„ ๊ฐ€์ง€๋Š” ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•ด์„œ ์—…๋ฐ์ดํŠธ ํ•ด์ฃผ๋Š” ๊ฒƒ์ด๋‹ค.

2. state๊ฐ€ ๋ณ€๊ฒฝ๋˜์ง€ ์•Š์Œ์—๋„ props๋ฅผ ์—…๋ฐ์ดํŠธ ํ•˜๋Š” ๊ฒฝ์šฐ

์ด ์ผ€์ด์Šค๋Š” ๋ถˆ๊ฐ€๋Šฅํ•ด๋ณด์ด์ง€๋งŒ ์ถฉ๋ถ„ํžˆ ๋ฐœ์ƒํ•  ์ˆ˜ ์žˆ๋Š” ์ƒํ™ฉ์ด๋‹ค. ๊ทธ๋ฆฌ๊ณ  ๋ณดํ†ต์€ ๋ฒ„๊ทธ๋ฅผ ๋ฐœ์ƒ์‹œํ‚จ๋‹ค. ์•„๋ž˜๋Š” ๊ทธ ์˜ˆ์‹œ๋กœ ์‹œ๊ณ„๋ฅผ ๋ณด์—ฌ์ฃผ๋Š” ์•ฑ์ด๋‹ค. ์ด ์‹œ๊ณ„๋Š” ์ฒ˜์Œ ๋ Œ๋”๋ง ๋œ ์ดํ›„ ์‹œ๊ฐ„์ด ๋ณ€ํ•˜์ง€ ์•Š๋Š”๋‹ค๋Š” ๋ฌธ์ œ๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๋‹ค.

setMyTime ํ•จ์ˆ˜๋Š” ๊ฐ€๋…์„ฑ์ด ์ข‹์ง€ ์•Š๊ณ , React ์ปดํฌ๋„ŒํŠธ์—๊ฒŒ ์ข‹์€ ์ฝ”๋“œ๋Š” ์•„๋‹ˆ๋‹ค.

function App() {
  let myTime;

  function setMyTime() {
    myTime = new Date();
    setTimeout(() => {
      setMyTime();
    }, 1000);
  }

  setMyTime();

  return (
    <div className="App">
      <Clock myTime={myTime} />
    </div>
  );
}

function Clock(props) {
  return <p>Current time: {props.myTime.toString()}</p>;
}

App ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์ฒ˜์Œ ๋ Œ๋”๋ง ๋˜๋ฉด์„œ setMyTime ํ•จ์ˆ˜๊ฐ€ ํ˜ธ์ถœ๋œ ์ดํ›„, ๋งค ์ดˆ๋งˆ๋‹ค setMyTime ํ•จ์ˆ˜๊ฐ€ ์žฌ๊ท€ํ˜ธ์ถœ ๋˜๋ฉด์„œ myTime์— ์‹œ๊ฐ„์„ ์žฌํ• ๋‹นํ•˜๊ณ , ๋ฆฌ๋ Œ๋”๋ง์„ ์œ„ํ•ด Clock ์ปดํฌ๋„ŒํŠธ์— ์ „๋‹ฌํ•œ๋‹ค. ๊ทธ๋Ÿผ์—๋„ ๋ถˆ๊ตฌํ•˜๊ณ  ๋ฆฌ๋ Œ๋”๋ง์ด ๋˜์ง€ ์•Š๋Š” ์ด์œ ๋Š” App ์ปดํฌ๋„ŒํŠธ๊ฐ€ myTime์˜ ๋ณ€ํ™”๋ฅผ ์•Œ์•„์ฐจ๋ฆฌ์ง€ ๋ชปํ•˜๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค.

React์—์„œ ์ปดํฌ๋„ŒํŠธ์˜ ์ƒํƒœ๋ฅผ ์—…๋ฐ์ดํŠธ ํ•˜๊ณ  ๊ด€๋ฆฌํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ์•„๋ž˜์ฒ˜๋Ÿผ useState๋ฅผ ์‚ฌ์šฉํ•ด ์ƒํƒœ์™€ ์—…๋ฐ์ดํŠธ ํ•จ์ˆ˜๋ฅผ ์ •์˜ํ•ด์•ผ ํ•œ๋‹ค. ์ถ”๊ฐ€์ ์œผ๋กœ useEffect๋ฅผ ์‚ฌ์šฉํ•ด ์ปดํฌ๋„ŒํŠธ๊ฐ€ ์–ธ๋งˆ์šดํŠธ ๋  ๋•Œ clearInterval์„ ํ•ด์„œ ๋ฒ„๊ทธ๋ฅผ ๋ฐฉ์ง€ํ•  ์ˆ˜ ์žˆ๋‹ค.

const [myTime, setMyTime] = useState(new Date());

 useEffect(() => {
   var timerID = setInterval(() => tick(), 1000);

   return () => clearInterval(timerID);
 });

 function tick() {
   setMyTime(new Date()); 
 }

๊ฐ•์ œ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฆฌ๋ Œ๋”๋ง ํ•˜๋Š” ๋ฐฉ๋ฒ•

๊ฐ•์ œ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฆฌ๋ Œ๋” ํ•˜๋Š” ๊ฒƒ์€ ๋Œ€์ฒด๋กœ ์ถ”์ฒœ๋˜๋Š” ๋ฐฉ๋ฒ•์ด ์•„๋‹ˆ๋‹ค. ์ปดํฌ๋„ŒํŠธ๊ฐ€ ๋ฆฌ๋ Œ๋”๋ง ๋˜์ง€ ์•Š๋Š” ๊ฒฝ์šฐ ๋Œ€๋ถ€๋ถ„์€ ์ฝ”๋“œ์ƒ์˜ ์˜ค๋ฅ˜๋กœ ์ธํ•œ ๊ฒƒ์ด๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค. ํ•˜์ง€๋งŒ ๋งŒ์•ฝ์— ์ •๋ง๋กœ ๊ฐ•์ œ ๋ฆฌ๋ Œ๋”๋ง์ด ํ•„์š”ํ•œ ๊ฒฝ์šฐ๋ผ๋ฉด, ๋ฐฉ๋ฒ•์ด ์—†๋Š” ๊ฒƒ์€ ์•„๋‹ˆ๋‹ค.

1. ํด๋ž˜์Šคํ˜• ์ปดํฌ๋„ŒํŠธ

ํด๋ž˜์Šคํ˜• ์ปดํฌ๋„ŒํŠธ์—์„œ๋Š” ๊ณต์‹์ ์œผ๋กœ ๋ฆฌ๋ Œ๋”๋ฅผ ๊ฐ•์ œํ•˜๋Š” API๊ฐ€ ์ œ๊ณต๋œ๋‹ค. ๋ฐ”๋กœ forceUpdate() ๋ฉ”์„œ๋“œ์ด๋‹ค.

someMethod() {
   // ์ƒํƒœ์˜ ๋ณ€ํ™” ์—†์ด๋„ ๊ฐ•์ œ๋กœ ๋ Œ๋”๋ง ํ•œ๋‹ค
   this.forceUpdate();
}

this.forceUpdate()๋ฅผ ํ˜ธ์ถœํ•˜๋ฉด shouldComponentUpdate()๋ฅผ ๊ฑด๋„ˆ๋›ฐ๊ณ  render() ๋ฉ”์„œ๋“œ๊ฐ€ ํ˜ธ์ถœ๋˜๊ธฐ ๋•Œ๋ฌธ์— ์ƒํƒœ์˜ ๋ณ€ํ™”๊ฐ€ ์—†์Œ์—๋„ React๊ฐ€ ๊ฐ€์ƒ DOM๊ณผ DOM์˜ ์ƒํƒœ๋ฅผ ์žฌ๋น„๊ตํ•˜๋„๋ก ๊ฐ•์ œํ•  ์ˆ˜ ์žˆ๋‹ค. ์—ฌ๊ธฐ์—๋Š” ๋ช‡ ๊ฐ€์ง€ ์œ ์˜ ์‚ฌํ•ญ์ด ์žˆ๋‹ค.

  • React์—์„œ ์ž์‹ ์ปดํฌ๋„ŒํŠธ๋Š” shouldComponentUpdate()๋ฅผ ํฌํ•จํ•œ ์ผ๋ฐ˜์ ์ธ ๋ผ์ดํ”„์‚ฌ์ดํด ๋ฉ”์„œ๋“œ๋“ค์— ์˜ํ•ด ์ž‘๋™๋˜๋ฏ€๋กœ, ๋ฆฌ๋ Œ๋”๋ง์„ ๊ฐ•์ œํ•  ์ˆ˜ ์žˆ๋Š” ๊ฑด ์˜ค์ง ํ˜„์žฌ ์ปดํฌ๋„ŒํŠธ ๋ฟ์ด๋‹ค.
  • ๊ฐ•์ œ ๋ฆฌ๋ Œ๋”๋ง์„ ํ•ด๋„ ์—ฌ์ „ํžˆ ๊ฐ€์ƒ DOM์€ DOM์˜ ์ƒํƒœ์™€ ๋น„๊ตํ•˜์—ฌ ๋ฆฌ๋ Œ๋”์˜ ์œ ํšจ์„ฑ์„ ํŒ๋‹จํ•˜๊ธฐ ๋•Œ๋ฌธ์—, ๋งˆํฌ์—…์˜ ๋ณ€ํ™”๊ฐ€ ์žˆ์„ ๋•Œ๋งŒ DOM์ด ์—…๋ฐ์ดํŠธ ๋  ๊ฒƒ์ด๋‹ค.

2. ํ•จ์ˆ˜ํ˜• ์ปดํฌ๋„ŒํŠธ

ํ•จ์ˆ˜ํ˜• ์ปดํฌ๋„ŒํŠธ์—์„œ๋Š” ๋ฆฌ๋ Œ๋”๋ฅผ ๊ฐ•์ œํ•˜๋Š” ๊ณต์‹ API๊ฐ€ ์กด์žฌํ•˜์ง€ ์•Š๋Š”๋‹ค. ๋•Œ๋ฌธ์— ๋ช‡๊ฐ€์ง€ ํŠธ๋ฆญ์„ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค.

  1. ์ƒํƒœ ๊ฐ์ฒด๋ฅผ ์ƒˆ๋กœ์šด ์ฐธ์กฐ๊ฐ’์„ ๊ฐ€์ง€๋Š” ๊ฐ์ฒด๋กœ ๋ฐ”๊พธ๊ธฐ
someMethod() {
   // ์ƒํƒœ๊ฐ€ ๋ณ€ํ•œ ๊ฒƒ์ฒ˜๋Ÿผ ํ‰๋‚ด๋‚ด ๊ฐ•์ œ๋กœ ๋ Œ๋”๋ง ํ•œ๋‹ค
   setUser({ ...user });
}

user๊ฐ€ ๊ฐ์ฒด์ด๊ณ  React๋Š” ์–•์€ ๋น„๊ต๋ฅผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์— spread ์—ฐ์‚ฐ์ž๋ฅผ ์‚ฌ์šฉํ•ด์„œ ์ƒˆ๋กœ์šด ์ฐธ์กฐ๊ฐ’์„ ๊ฐ€์ง€๋Š” ๊ฐ์ฒด๋กœ ์—…๋ฐ์ดํŠธ ํ•œ๋‹ค๋ฉด, React๋Š” ์ƒํƒœ๊ฐ€ ๋ณ€๊ฒฝ๋˜์—ˆ๋‹ค๊ณ  ํŒ๋‹จํ•ด ๋ฆฌ๋ Œ๋”๋ฅผ ํ•˜๋Š” ๊ฒƒ์ด๋‹ค. ์ด๋Š” ์ƒํƒœ๊ฐ€ ๊ฐ์ฒด๋‚˜ ๋ฐฐ์—ด์ธ ๊ฒฝ์šฐ์— ์ ์šฉํ•  ์ˆ˜ ์žˆ๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค.

  1. ๋นˆ ์ƒํƒœ ๋ณ€์ˆ˜๋กœ ์—…๋ฐ์ดํŠธ ๋ฐœ์ƒ์‹œํ‚ค๊ธฐ

useState๋กœ ์—…๋ฐ์ดํŠธ ํ•จ์ˆ˜๋งŒ ์„ ์–ธํ•˜๊ณ , ๊ฐ•์ œ๋กœ ๋ฆฌ๋ Œ๋”๋ง์ด ํ•„์š”ํ•  ๋•Œ ์ƒˆ๋กœ์šด ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•ด ์—…๋ฐ์ดํŠธ ํ•˜๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค.

import { useState, useCallback } from "react";

function App() {
 const [, updateState] = useState(); // ์ƒํƒœ ๋ณ€์ˆ˜๋Š” ์„ ์–ธํ•˜์ง€ ์•Š๋Š”๋‹ค
 const forceUpdate = useCallback(() => updateState({}), []);

 console.log("rendering...");

 return (
   <div className="App">
     <h1>Time to force some updates</h1>
     <button onClick={forceUpdate}>Force re-render</button>
   </div>
 );
}

๊ทธ๋Ÿผ ์ด์ œ Force re-render ๋ฒ„ํŠผ์„ ๋ˆ„๋ฅผ ๋•Œ๋งˆ๋‹ค ์ปดํฌ๋„ŒํŠธ๊ฐ€ ๋ฆฌ๋ Œ๋” ๋˜์–ด ์ฝ˜์†”์— ๋กœ๊ทธ๊ฐ€ ์ฐํž ๊ฒƒ์ด๋‹ค. ์ด ๋•Œ useCallback์„ ์‚ฌ์šฉํ•ด ์ฒซ ๋ Œ๋” ์‹œ์˜ forceUpdate ํ•จ์ˆ˜๋ฅผ ๋ฉ”๋ชจ๋ฆฌ์— ์ €์žฅํ•ด๋†“๊ณ , ์ž์‹ ์ปดํฌ๋„ŒํŠธ์˜ props๋กœ ์•ˆ์ „ํ•˜๊ฒŒ ์ „๋‹ฌํ•˜๋„๋ก ํ•œ๋‹ค.

๊ฒฐ๋ก 

๋ฐ˜๋ณตํ•ด ์–˜๊ธฐํ•˜์ง€๋งŒ ๊ฐ•์ œ๋กœ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋ฆฌ๋ Œ๋” ํ•˜๋Š” ๊ฑด ์ข‹์€ ๋ฐฉ๋ฒ•์ด ์•„๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ์ผ์ด ์ผ์–ด๋‚˜์ง€ ์•Š๋„๋ก ์ข‹์€ ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•˜๋Š” ๊ฒƒ์ด ์šฐ์„ ๋˜์–ด์•ผ ํ•œ๋‹ค.