reactの関数コンポーネントを学習する際に必ず必要となるuseState,useEffectの使い方に関してまとめます。
ステートフック【useState】
ステートフックは、「ステート」のためのフックです。
ステートは、値をコンポーネント内で保持し、その値を更新することで表示も更新できる特別な値です。
このステートフックは「useState」という関数として用意されており、以下のように利用します。
const [変数A, 変数B] = useState(初期値)
useStateはステートを作成するためのものです。
引数には、そのステートの初期値を指定し、
戻り値は、2つの値が返される。上の[変数A, 変数B]という2つの変数に、戻り値がそれぞれ代入されます。
この2つの変数には、以下のようなものが返されます。
- 変数A:ステートの値。ここから現在のステートの値が得られる。
- 変数B:ステートの値を変更する関数。この変数に引数をつけて呼び出すことでステートの値が変更される。変数の名前は「set変数A」とすることが通例となっています。
ステートを初期化する
import { useState } from "react";
function hook() {
const [name, setName] = useState("");
return (
<p>こんにちわ{name}です。</p> // => こんにちわ鈴木です。
)
}
ステートの値を利用する
ReactのJSX内でステートの値を利用する方法はJSXの中で波かっこ{} を記述し、その中でステートの変数を使用するだけです。
import { useState } from "react";
function hook() {
const [name, setName] = useState("鈴木");
return (
<p>こんにちわ{name}です。</p> // => こんにちわ鈴木です。
)
}
ステートの値を更新する
ステートを更新するには、useStateの結果返ってきた2つ目のステート更新関数(変数B)を使用します。
import { useState } from "react";
function hook() {
const [name, setName] = useState("鈴木");
return (
<>
<p>こんにちわ{name}です。</p>
<button
onClick={() => setName("渡辺")}
>名前変更</button>
</>
)
}
副作用フック【useEffect】
ステートは、値を変更すると自動的に表示が更新されましたね。
ステートが直接表示に使われていないところは、ステートが変更されても更新はされません。
しかし、ページにアクセスしたり表示が更新されたりした際に何らかの処理を実行したりすることはあるでしょう。
例えば、サーバーにアクセスしてデータを取得し利用するようなときなどは必要に応じてアクセスし最新のデータを取得しなければいけないこともある。
このようなときのために「副作用フック」が用意されています。
副作用フックは以下のように記述します。
useEffect(関数)
副作用フックを利用する
import React, { useState, useEffect } from "react";
function hook() {
let [count, setCount] = useState(0);
useEffect(() => {
console.log("レンダーされました。");
});
return (
<>
<button onClick={() => setCount(count + 1)}>
カウントアップ
</button>
<p>{count}</p>
</>
);
};
上記の記述は、レンダリングされる度にuseEffectが動き、コンソール上に「レンダーされました」と表示させます。
useEffectで関数を設定しておくだけで、コンポーネントがマウントされたり表示が更新されたりした際には指定の関数が実行されるようになります。
レンダリングされるたびに動くと最初は認識しても大丈夫だと思います。
再呼び出しフックを指定する
しかし、以下のような記述に変えた場合はレンダリングされるたびにuseEffectが動くと無限に呼び出しを続けてしまう不都合が起きてしまいます。開発者ツールのコンソールを見てみるとたくさんuseEffectが呼び出されていてエラーになっています。
import React, { useState, useEffect } from "react";
function hook() {
const [count, setCount] = useState(0); //クリックされた数をカウントする
const [num, setNum] = useState(0) //レンダリングされた回数
useEffect(() => {
setNum(num +1)
console.log(num + "回レンダーされました。");
});
return (
<>
<button onClick={() => setCount(count + 1)}>
カウントアップ
</button>
<p>{count}</p>
</>
);
};
無限に自分自身の呼び出しを続けてしまうことを回避するために、useEffectの際に以下のように引数を追加する必要があります。
useEffect(関数,[ステート])
第2引数に、ステートの配列を指定します。第2引数の配列に指定したステートが更新されたときは、この副作用フックを最後呼び出すことが許可されます。それ以外の場合は、再度呼び出されないようになります。
上記のエラー無限に呼び出してた記述を以下のように記述することで、無限呼び出しが解消されます。
import React, { useState, useEffect } from "react";
function hook() {
const [count, setCount] = useState(0); //クリックされた数をカウントする
const [num, setNum] = useState(0) //レンダリングされた回数
useEffect(() => {
setNum(num +1)
console.log(num + "回レンダーされました。");
},[count]);
return (
<>
<button onClick={() => setCount(count + 1)}>
カウントアップ
</button>
<p>{count}</p>
</>
);
};
最初にレンダリングされた際とcountの値が更新されたときのみuseEffectが動くようになりました。
ちなみに、第2引数をuseEffect(関数,[ ])のように空の配列にすると最初にレンダリングされた際のみuseEffectが動きます。
コメント