[React] useMemo


useMemo


userMemoとは?

const memoizedValue = useMemo(() => computeExpensiveValue(a, b), [a, b]);
は、注釈の値を返します.
useMemoは、最初に計算した計算値をメモリに格納し、素子が繰り返しレンダリングされても、以前に計算した値をメモリから取り出すことができます.
2番目のパラメータ値の配列が変更されるたびに、コメントが現在完了している値が取り出され、その配列が空の場合、1番目の構成部品がマウントされている場合にのみ値が計算され、計算値が取り出されます.
import React, { useMemo, useState } from "react";

//컴포넌트 밖에다가 선언하면 함수의 불필요한 초기화를 막을 수 있다
const hardCalculate = (number) => {
  console.log("어려운 계산!");
  for (let i = 0; i < 999999999; i++) {} // 생각하는 시간
  return number + 10000;
};

const easyCalculate = (number) => {
  console.log("짱 쉬운 계산!");
  return number + 1;
};

function Memo() {
  const [hardNumber, setHardNumber] = useState(1);
  const [easyNumber, setEasyNumber] = useState(1);
  const hardSum = useMemo(() => {
    return hardCalculate(hardNumber);
  }, [hardNumber]);
  const easySum = easyCalculate(easyNumber);
  return (
    <div>
      <h3>어려운 계산기</h3>
      <input
        type="number"
        value={hardNumber}
        onChange={(e) => setHardNumber(parseInt(e.target.value))}
      />
      <span> + 10000 = {hardSum}</span>
      <h3>쉬운 계산기</h3>
      <input
        type="number"
        value={easyNumber}
        onChange={(e) => setEasyNumber(parseInt(e.target.value))}
      />
      <span> + 1 = {easySum}</span>
    </div>
  );
}
上記のコードにuserMemoが使用されていない場合、簡単な計算機をクリックしてもハード計算が実行されるため、1秒の遅延が発生します.ただし、useMemoを使用している場合は、ハード番号を変更した場合にのみ関数を実行するため、容易な計算機は正常に動作します.
実際のコードでは,上記1秒以上の関数で素子内部の変数を初期化することはあまり見られない.したがって,useMemoが発光する場合,論理は以下のようになる.
import React, { useEffect, useState } from "react";

function Memo() {
  const [number, setNumber] = useState(0);
  const [isKorea, setIsKorea] = useState(true);

  const location = isKorea ? "한국" : "외국";
  useEffect(() => {
    console.log("useEffect 호출");
  }, [location]);
  return (
    <div>
      <h3>하루에 몇끼 드심?</h3>
      <input
        type="number"
        value={number}
        onChange={(e) => setNumber(e.target.value)}
      />
      <hr />
      <h3>지금 어디?</h3>
      <p>나라: {location}</p>
      <button onClick={() => setIsKorea(!isKorea)}>비행기 타고 가요~</button>
    </div>
  );
}
useEffectの依存配列にlocationを加えているのでnumberを変えてもconsoleは撮れません.ただし、下図のようにlocationがオブジェクトであればnumberを変更してもコンソールが写っています.オブジェクトは元のタイプではなく、オブジェクトタイプだからです.
import React, { useEffect, useState } from "react";

function Memo() {
  const [number, setNumber] = useState(0);
  const [isKorea, setIsKorea] = useState(true);

  const location = { country: isKorea ? "한국" : "외국" };
  useEffect(() => {
    console.log("useEffect 호출");
  }, [location]);
  return (
    <div>
      <h3>하루에 몇끼 드심?</h3>
      <input
        type="number"
        value={number}
        onChange={(e) => setNumber(e.target.value)}
      />
      <hr />
      <h3>지금 어디?</h3>
      <p>나라: {location.country}</p>
      <button onClick={() => setIsKorea(!isKorea)}>비행기 타고 가요~</button>
    </div>
  );
}

ちょっと待って。ここで、「オリジナル」(Primitive)タイプと「オブジェクト」(Object)タイプは?


元のタイプはString、Number、Bigint、Boolean、Undefind、Symbol、Nullであり、オブジェクトタイプはObject、Arrayである.元のタイプの値には直接値が含まれますが、オブジェクトタイプの値はサイズによってメモリの領域に割り当てられ、メモリに保存されます.変数にはオブジェクトを含むメモリが割り当てられます.
したがって、同じ値を含む他の変数を比較する場合、元のタイプはTrueですが、オブジェクトが他のメモリに割り当てられているため、他のアドレスを比較するため、Falseが表示されます.したがって、前のコードでレンダリングすると、新しいlocationオブジェクトのメモリが前のlocationで参照したメモリとは異なるため、コンソールが撮影されます.
したがって、次のようにコードを変更します.
import React, { useEffect, useMemo, useState } from "react";

function Memo() {
  const [number, setNumber] = useState(0);
  const [isKorea, setIsKorea] = useState(true);

  const location = useMemo(() => {
    return {
      country: isKorea ? "한국" : "외국",
    };
  }, [isKorea]);

  useEffect(() => {
    console.log("useEffect 호출");
  }, [location]);
  return (
    <div>
      <h3>하루에 몇끼 드심?</h3>
      <input
        type="number"
        value={number}
        onChange={(e) => setNumber(e.target.value)}
      />
      <hr />
      <h3>지금 어디?</h3>
      <p>나라: {location.country}</p>
      <button onClick={() => setIsKorea(!isKorea)}>비행기 타고 가요~</button>
    </div>
  );
}

注意事項


userMemoに渡される関数はレンダリング中に実行されるため、userMemoの関数では、効果図などのレンダリング中にサイトがしないことを処理することはできません.
useMemoはメモリを消費するので、必要に応じてのみ使用することが望ましい.

参考文献


https://ko.reactjs.org/docs/hooks-reference.html#usememo
https://www.youtube.com/watch?v=e-CnI8Q5RY4
https://developer.mozilla.org/ko/docs/Web/JavaScript/Data_structures