🤹🏻‍♀️

Reactの状態を理解して適切にHooksを利用する

に公開
5
GitHubで編集を提案

Discussion

Honey32Honey32

細かいところで失礼します

filteredTodo については、

const [filter, setFilter] = useState<"marked" | "unmarked" | "all">("all");
const filteredMemo = (
   filter === "marked"
   ? memos.filter((memo) => memo.marked)
       : filter === "unmarked"
       ? memos.filter((memo) => !memo.marked)
         : memos
);

と生の式 + 三項演算子を使って書くほうが良いと思います。

もしくは、計算結果がキャッシュされることを除いて同じ意味になりますが、useMemo を使うことが多いです。(useMemo の中はアロー関数が書けるため、三項演算子を使わなくて済むので)

const [filter, setFilter] = useState<"marked" | "unmarked" | "all">("all");
const filteredMemo = useMemo(() => {
   if (filter === "marked") return memos.filter((memo) => memo.marked);
   if (filter === "unmarked") return memos.filter((memo) => !memo.marked);
   return memos;
}, [filter, memo]);

filterMemos(filter) のような形でも正しく動きはしますが、上記のように生の三項演算子を使った式 or useMemo で書くことで、「filteredMemo は、filter, memo から計算できる状態である」 (この言い回しは react.dev/learn にも度々登場します)と意識することが出来て意図の共有がしやすいと思います。

sakusaku

コメントありがとうございます!

1番目の改善提案に関しては、私の書き方をこの場合三項演算子で書いた方が良いというものですね!

2番目の改善提案にある、useMemoを使用する意図がとても勉強になります!🙌🏻
確かにフックの依存配列は発火タイミングを明示してあげることができるという働きもありました。
加筆しておきます!

Honey32Honey32

少しでも学習のお役に立てたなら幸いです!

(コードのタイポ、意図の不明確な文章を少し修正しました)

クロパンダクロパンダ

メチャクチャよくまとまってますね…!

読んでる途中ですが、「useCallback 重たい関数をキャッシュするためのフック」の部分は誤りと思います。重たい関数というものがそもそもなく、レンダーごとに関数が再生成される→関数は参照が等しくないと等価とみなされないのが問題であり、「重いかどうか」は関係ないので

(後ろの「レンダー前後でuseCallback依存配列の値に差異がない場合に関数の再生成をスキップしてくれるフックです。」の説明は合ってるので、重い関数云々のとこピンポイントでのミスだと思います)

sakusaku

読んでいただきありがとうございます🌟

確かに、実行コスト(「重さ」)ゆえuseCallbackを使っているのではないですね...!
Profilerなどで測定した結果、著しくパフォーマンスに影響を与えているコンポーネントが関数propsを受けていた場合に、その関数定義をuseCallbackでキャッシュ&コンポーネントをmemo化してあげることでパフォーマンス改善の第一歩を踏み出せるという理解でした。
「重たいコンポーネントをキャッシュしたいときに併用が考えられるフック」というイメージですが、単に「関数をキャッシュするためのフック」と修正しておきます!