Array.filter
Array.filter とは
filter で条件に合う要素だけを残す。本レッスンでは、Array.filter の基本から実際の使いどころまでを整理し、現場で迷わず使える形に落とし込みます。
filter で要素を絞り込む
map が 加工 なら、 filter は 絞り込み です。 Array.prototype.filter は配列の各要素に 条件 を与え、 true を返した要素だけを集めて新しい配列にしてくれます。 for と if を使えば自分でも書けますが、 filter を使うとぐっと短く読みやすくなります。
filterは配列を短くするメソッド、mapは配列の中身を変えるメソッド、と覚えると区別しやすいです。要素数はfilterで減ることはあっても増えることはありません。
例えば「配列の中から偶数だけ取り出す」「ログインしているユーザーだけ残す」 「不要なデータを除外する」などに使えます。 JavaScript の現場で for ループを書く前に、まず filter で書けないか考える癖をつけましょう。
filter の文法
書き方は次のとおりです。
JavaScript
const nums = [1, 2, 3, 4, 5, 6];
const evens = nums.filter((n) => n % 2 === 0);
console.log(evens); // [2, 4, 6]
console.log(nums); // [1, 2, 3, 4, 5, 6] (元のまま)コールバックは 要素 を受け取り、 boolean を return します。 true なら残す、 false なら捨てる、というシンプルなルールです。
filter のコールバックも (element, index, array) の 3 引数を受け取れますが、ほとんどの場合は element だけで足ります。
JavaScript
const arr = [10, 25, 8, 14, 99];
const over20 = arr.filter((n) => n > 20);
console.log(over20); // [25, 99]コールバックの戻り値は厳密に
true/falseではなくtruthy/falsyでも構いません。例えばarr.filter(Boolean)でnullや0、空文字を一気に取り除けます。
動きを追ってみる
filter のフローはこんな感じです。
各要素について 条件を満たすか を判定し、満たすものだけを新しい配列に集めるだけです。 map と組み合わせて filter().map() のように繋ぐと、 絞り込んでから加工 の流れも 1 行で書けます。
for + if と比較する
手書きでループを回した場合と比べてみます。
JavaScript
// for + if 版
const nums = [1, 2, 3, 4, 5, 6];
const evens = [];
for (let i = 0; i < nums.length; i++) {
if (nums[i] % 2 === 0) evens.push(nums[i]);
}
// filter 版
const evens2 = nums.filter((n) => n % 2 === 0);for + if 版は i の管理や push の手順が見えますが、 filter 版は 条件 だけが残ります。条件式に名前を付ければさらに読みやすくなります。
JavaScript
const isEven = (n) => n % 2 === 0;
const evens3 = nums.filter(isEven);条件式を別の関数に切り出すと、テストもしやすくなり、複数の場所で再利用できます。
関数を値として扱う高階関数のうれしさです。
filter ではできないこと
以下のとおりです。
- 要素を加工して別の値にしたい → それは
mapの仕事 - 配列を 1 つの値にまとめたい → それは
reduceの仕事 - 元の配列を直接削りたい →
spliceなどを使うが、できるだけfilterで新しい配列を作る方が安全
filter は 元を変えない ので、 React などの状態管理とも相性抜群です。元の state を変更せずに 新しい配列 を作って差し替える、という流れにぴったりはまります。
よくある間違い
よくあるつまずきは次のとおりです。
filterのコールバックでreturnを書き忘れて、全要素が落ちる (undefinedは falsy)filterの戻り値を捨ててしまい、元配列が変わると勘違いする=と===を間違えて、比較のつもりが代入になっている
JavaScript
const arr = [1, 2, 3];
// NG — 戻り値を使っていない、元配列も変わらないので何も起きない
arr.filter((n) => n > 1);
console.log(arr); // [1, 2, 3]
// OK — 戻り値を変数に受ける
const filtered = arr.filter((n) => n > 1);
console.log(filtered); // [2, 3]戻り値を変数に受けないなら
filterを使う意味はありません。forEachを使うべき場面と区別しましょう。
やってみよう
配列 arr を受け取り、 filter を使って偶数だけ残した新しい配列を返す関数 keepEvens を書いてみましょう。元の配列は変更しません。空配列 [] のときは [] を返します。
よくある質問
Q. filter と find の違いは?
A. filter は条件を満たす要素を全部集めて配列で返し、find は最初に見つかった 1 件だけ返します。1 件だけ欲しいなら find の方が短絡評価で速く、空のとき undefined(Python の next は StopIteration)になる点に注意してください。
Q. filter の戻り値が空配列のときの扱いは?
A. JS の filter は常に配列を返すため、空でも .length で安全にチェックできます。Python の filter はイテレータを返すので list() で囲んでから使うか、内包表記 [x for x in items if cond] の方が分かりやすいことが多いです。
Q. filter と map をチェーンしても性能は大丈夫ですか?
A. 通常規模なら問題ありません。配列を 2 周することになるため、要素数が数百万を超える場合だけ reduce にまとめるか、JS なら array.reduce で 1 周にすることを検討してください。可読性は filter→map のチェーンが分かりやすいです。
次のレッスン
次は Array.reduce で、filter で条件に合う要素だけを残す を学びます。
事前確認 — 進む前に次の 3 つができることを確認しましょう。
- Array.filter の要点を自分の言葉で説明できる
- このレッスンの最小コード (または操作手順) を見ずに書ける
- 練習問題やクイズで間違えた箇所を読み直して理解した
理解度チェック (30 秒)
Q. Array.filter とは何か、1 文で説明してください。
A. 本文の「このレッスンで分かること」または冒頭の説明文を見直し、自分の言葉で要約できれば OK。詰まったら本レッスンの最初の H2 セクションを読み返してみましょう。
関連レッスン
要件
- Array.prototype.filter を使う
- n % 2 === 0 で偶数判定する
- 条件に合う要素だけ残した新しい配列を return する
入出力例
test-cases.txt
keepEvens([1,2,3,4,5,6]) → [2,4,6]
keepEvens([]) → []
keepEvens([1,3,5]) → []
keepEvens([0,-2,7,8]) → [0,-2,8]