【入門編】 無限ループの発生原因とデバッグ手法 – React実践ガイド

こんにちは!Reactの学習、楽しく進めていますか?それとも……今まさに画面が固まったり、ブラウザのファンが「ブオーーーッ!」と凄まじい音を立てて回り出したりして、冷や汗をかいているところでしょうか?

「画面が真っ白になった」
「コンソールにエラーが何万行も流れた」
「パソコンが急に熱くなった!」

大丈夫です、深く息を吸ってください。あなたが悪いわけでも、プログラミングの才能がないわけでもありません。これは誰もが、本当に誰もが一度は通る「Reactの洗礼」、無限ループという名の小さなしいたげられた罠にハマってしまっただけなのです。

今日は、この無限ループがなぜ起きるのか、身近な例えを交えながら、ふんわりと、でも確実に紐解いていきましょう。

—

1. なぜ「無限ループ」は起きるのか?(おしゃべりな鏡の例え)

Reactの `useEffect` という機能は、いわば「お部屋の見張り番」のようなものです。
「お部屋の模様替え(状態の変化)があったら、何か教えてね」とお願いする仕組みになっています。

ここで、こんな状況を想像してみてください。

あなたは今、自分の姿を鏡でチェックしています。
1. あなたが「あれ、髪型が崩れてるな」と気づいて手で直す(状態の更新)
2. 鏡に映る自分が変わる
3. それを見たあなたが「あ、また髪型が変わった!直さなきゃ!」と勘違いして、また手を動かす(副作用の再実行)
4. 1に戻る……

これが、無限ループの正体です。「自分で自分の状態を変えたのに、それを『外からの変化』だと勘違いして、延々と自分を直し続ける」という終わらないおしゃべりです。

Reactのコードで書くと、こういう状態です。

import { useState, useEffect } from ‘react’;

function InfiniteLoopExample() {
const [count, setItems] = useState(0);

useEffect(() => {
// 【事件現場】ここで状態を更新しています
// 「カウントが変わったよ!」と報告するつもりが、自分でカウントを増やしてしまっている
setItems(count + 1);
}, [count]); // 依存配列に「count」が入っている!

return

現在のカウント: {count}

;
}

`useEffect` の中身が実行されて `count` が変わる → `count` が変わったから `useEffect` がもう一度呼ばれる → また `count` が変わる……。
まさに、終わりなきメリーゴーランドの完成です。

—

2. 犯人は誰だ?無限ループの特定方法(React DevToolsを使おう)

「なんか画面がフリーズする……どこが原因なの!?」
そんなとき、私たちの強力な相棒になってくれるのが 「React DevTools」 というブラウザの拡張機能です(ChromeやFirefoxで使えます)。

これを使うと、どのコンポーネントが狂ったように再レンダリング(再描画)を繰り返しているかが一目でわかります。

デバッグの手順

1. ブラウザで開発者ツールを開き、「Profiler」 というタブを開きます。
2. 録画ボタン(丸い赤いボタン)を押します。
3. アプリを少し操作して、フリーズする瞬間を再現します。
4. 録画を停止すると、「どのコンポーネントが何回再描画されたか」がグラフや炎のような色(熱い部分ほど赤くなります)で表示されます。

もし、ひとつのコンポーネントが「数秒の間に何千回も再描画されている!」となれば、そこが犯人(無限ループの発生源)です。大抵の場合、`useEffect` の依存配列の書き忘れや、状態更新のミスが隠れています。

—

3. 大丈夫、こう書けば解決します!(実践的なコード)

では、どうすればこの無限ループを回避できるのでしょうか?
「状態を変えたときに、本当に毎回その処理が必要なのか?」を一度立ち止まって考えてみましょう。

例えば、「APIからデータを1回だけフッチ(取得)したい」という場合、依存配列を空っぽ `[]` にして、「最初にコンポーネントが表示されたときだけにしてくださいね」とお願いするのが正解です。

import { useState, useEffect } from ‘react’;

function SafeExample() {
const [user, setUser] = useState(null);

// 1回だけデータを取得したい!
useEffect(() => {
// ここでAPIを叩く処理など(今回はシミュレーション)
console.log(“データを取得しました!(これは最初に1回だけ呼ばれます)”);

// 仮のユーザーデータをセット
setUser({ name: ‘さくらちゃん’ });

}, []); // ★ここを空っぽにすることで、無限ループを完全に防ぎます!

return (

{user ?

こんにちは、{user.name}さん!

:

読み込み中…

}

);
}

もし、特定の変数が変わったときだけに反応させたい場合は、「その変数が本当にその副作用の中で更新されていないか」をよーーく確認してください。「副作用の中で、その依存配列の変数を `set〇〇` していないか?」。ここをチェックするだけで、9割の無限ループは防げます。

—

最後に:失敗は、Reactと仲良くなるためのステップ

いかがでしたでしょうか?
無限ループに出くわすと、「うわ、バグった!壊しちゃったかも……」と不安になるかもしれませんが、それはあなたのコードが元気に動き回っている証拠でもあります(ちょっと元気すぎますが!)。

Reactという相棒と上手に付き合うコツは、「誰が、何をきっかけに、何をするのか」を整理してあげること。

もしまたフリーズしちゃったら、慌てずにブラウザを閉じて、コードの `useEffect` の `[ ]` の中身をそっとのぞいてみてくださいね。
「あ、自分で自分のしっぽを追いかけてたんだな」って気づけたら、もうあなたは立派なReactエンジニアです。

今日も一緒に、楽しくコードを書いていきましょう!

コメント

タイトルとURLをコピーしました