第81章:Reactが画面を書き換える仕組み(再レンダリング)を知ろう
1. まずゴール 🎯
この章が終わるころには…
- 「再レンダリングってなに?」がふんわりイメージできる
- 「何が起きると再レンダリングされるのか」が分かる
- 「ボタン押したら画面が変わる」が、裏でどう動いてるかをイメージできる
- 次の章の
React.memoやuseCallbackの話にスムーズにつながる
完全に理解じゃなくてOKです。 「だいたいこんな流れなんだな〜」くらいで十分 👍
2. 「レンダリング」と「再レンダリング」ってなに?🧠
Reactの世界では、
- レンダリング(render) → 「この状態なら、画面はこういう見た目だよ〜」と 計算する 作業
- 再レンダリング(re-render) → いったん表示した後、新しい状態に合わせてもう一回計算する こと
というイメージです。
React公式サイトでは、
- レンダリング = コンポーネント関数を呼び出して JSX を計算すること
- そのあとに DOM を実際に書き換えるステップ(コミット) がある
という2段階で説明されています 🧩(React)
大事なのは 「コンポーネントがもう一度“実行される” = 再レンダリング」 というイメージです。
3. Reactが画面を変える「2ステップ」イメージ 🪄
Reactが画面を更新するとき、ざっくりこう動きます:
-
レンダーフェーズ(Render Phase)
- コンポーネント関数を呼び出す
- そこから JSX(= 仮想的な画面の姿)を作る
- 前回の結果(前の画面の姿)と比べて「どこが変わったか?」を計算する
-
コミットフェーズ(Commit Phase)
- 差分だけを実際の ブラウザのDOMに反映 する
- だから「全部作り直し」じゃなくて「変わったところだけ」更新される
この「仮想的な画面の姿」がいわゆる Virtual DOM で、 前の Virtual DOM と今の Virtual DOM を比べて、差分だけ更新する仕組みを 「リコンサイル(reconciliation)」 と呼びます 💡(ウィキペディア)
4. どんなときに「再レンダリング」されるの?🔁
Reactコンポーネントが 再レンダリング される主なタイミングは次のとおりです:(Developer Way)
-
useStateの値が変わったときsetCount(...)みたいにset〇〇を呼んだとき
-
親コンポーネントが再レンダリングされたとき
- 親がもう一度実行されると、子ももう一度実行される(※後で最適化できる)
-
Context (
useContext) の値が変わったとき- 共有しているデータが変わると、それを使っているコンポーネントが再レンダリング
-
その他、React内部で「これは更新が必要だな〜」と判断されたとき
とくに覚えておきたいのは:
✅ 「状態(state)の変化」が、ほとんどの再レンダリングのスタート地点
ということです。
5. シンプルなカウンターで裏側イメージ 🧮
かんたんなカウンターを例にして、 Reactがどう動いているかイメージしてみましょう 💭
import { useState } from "react";
export function Counter() {
const [count, setCount] = useState(0);
console.log("Counter コンポーネントが実行されました!");
return (
<div>
<p>今のカウント:{count}</p>
<button onClick={() => setCount(count + 1)}>
+1する
</button>
</div>
);
}
ブラウザの開発者ツールのコンソールを開いておくと、 ボタンを押すたびに
Counter コンポーネントが実行されました!
と表示されます。
これはつまり:
- ボタンをクリック
setCount(count + 1)が呼ばれる- React が「状態が変わった!」と気づく
Counterコンポーネントを もう一度実行(= 再レンダリング)- 新しい JSX を作って、前と差分を計算
- 変わったところだけ DOM に反映(
<p>の数字だけ)
という流れになっている、ということです ✨
6. Mermaidで見る「再レンダリング」の流れ 🧷📊
Reactの動きを図にしてみます。 (Mermaid対応エディタに貼ればフローチャートが表示されます💡)
「コンポーネントがもう一回実行される = 画面を全部書き直している …ように“見える”けど、実際には 差分だけ DOM を変えている」 という流れがポイントです 🌟
7. 「再レンダリング = DOMの全書き換え」ではないよ 🔍
よくある勘違いとして、
「再レンダリングされたら、画面が全部作り直されるんでしょ? それって重そう…💦」
というイメージがあるかもしれません。
実際には:
- コンポーネント関数は もう一度実行される(JSの計算)
- でも React は Virtual DOM の差分だけ 実際のDOMに反映する
- だから、思っているよりずっと効率的に動いています💨(ウィキペディア)
この「差分だけ更新する」おかげで、 開発者は
「この状態ならこんなUI!」
と 宣言的に書くだけでOK になるわけです ✨
8. React 19 の「中身」はどう変わってるの?ざっくりだけ 🧪
React 19 では、
-
レンダリングの仕組み自体(Virtual DOM → 差分 → DOM更新) は これまでと同じ考え方
-
ただし、
- JSX の変換や
- サーバーコンポーネント
- Actions /
useなどの新機能 - コンパイラによる自動最適化(将来的に)
などの 内部のエンジン部分がどんどん賢く なっています。(React)
この章で覚えておきたいのは、
React 19 でも 「状態 → レンダリング → 差分 → DOM更新」 という大きな流れは変わらない
ということです 🧠✨
9. ちょっとした実験アイデア 🧪✨
時間があったら、こんな遊びもしてみてください:
🧪 実験1:コンソールログで「何回実行されるか」見る
さっきの Counter に、あえて 重そうな処理っぽいログ を足してみます。
import { useState } from "react";
export function Counter() {
const [count, setCount] = useState(0);
console.log("🍰 Counter が実行されました");
// 重そうに見せるダミー処理
let total = 0;
for (let i = 0; i < 1_000_0; i++) {
total += i;
}
return (
<div>
<p>今のカウント:{count}</p>
<button onClick={() => setCount(count + 1)}>
+1する
</button>
</div>
);
}
- ボタンを押すたびに
🍰 Counter が実行されましたが増える → 再レンダリングが起きている証拠 - でも画面全体ではなく、 DOMとしては 必要な部分だけ更新 されています
※実際にパフォーマンスを最適化するときは、 次の章で出てくる
React.memo/useCallback/useMemoが登場します 💪
10. よくある疑問 Q & A 💬
Q1. 「再レンダリング」って悪いこと?
A. ぜんぜん悪くないです。むしろ普通のこと。
- React は「状態が変わったら再レンダリングする」前提で設計されています
- 小さいコンポーネントなら、多少たくさん再レンダリングしても ユーザーはほとんど気づきません
✨ 最適化(memo化)は「どうしても重くなってきたら」でOK このあと Module 10 全体でゆっくり学びます
Q2. 再レンダリングが起きたら、子コンポーネントも全部再レンダリング?
基本的には
親が再レンダリングされると、子も呼び出される
という動きになります。(Developer Way)
ただし:
React.memoや- 将来の React Compiler
などの仕組みを使うと、 「同じ Props なら、子はもう一回実行しなくていいよね」という 最適化ができるようになります。
これがまさに、この Module 10 のテーマ 🔥
11. まとめ ✨
この章のポイントをぎゅっとまとめると:
- ✅ レンダリング = コンポーネントを実行して JSX を計算すること
- ✅ 再レンダリング = 状態が変わってもう一度コンポーネントが実行されること
- ✅ Reactは Virtual DOM を使って、前回との差分だけ DOMを更新するから効率的
- ✅ 再レンダリングは「悪者」じゃなくて、Reactがちゃんと動いている証拠
- ✅ 「どこから再レンダリングが発生してるか」を意識できると、 Module 10 の最適化テクニックが理解しやすくなる
12. ミニクイズ 📝(頭の整理用)
※答えは声に出して答えるくらいでOKです。
- 再レンダリングが起きる主なきっかけを、2つ以上言えますか?
- 「レンダーフェーズ」と「コミットフェーズ」のちがいを、 1行ずつくらいで説明するとしたら?
setCount(count + 1)を呼ぶと、Reactの中ではどんな順番で処理されそう?
13. 宿題アイデア 💡
余裕があれば、こんなことをやってみてください:
-
小さなコンポーネントを2つ作る(親と子)
-
親にボタンを置いて、
useStateでカウントを増やす -
親と子それぞれに
console.log("親です"),console.log("子です")を入れて -
ボタンを押したとき、
- どのログが
- 何回 出るか観察してみる 👀
次の章(第82章)では、この「再レンダリングの仕組み」を前提に、
React.memo を使って「ムダな再レンダリング」を減らす テクニックに入っていきます 💪✨
もし、ここまでで 「ここの説明もうちょっとゆっくり聞きたい…!」 というところがあれば、どこでもピンポイントで聞いてくださいね 🥰