13
7

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

商品カテゴリで学ぶBFS(幅優先探索)

Last updated at Posted at 2025-07-18

幅優先探索(Breadth-First Search, BFS)は、グラフやツリー構造を探索する基本的なアルゴリズムの一つですが、「実務で使うイメージが湧かない…」という方も多いかもしれません。

私自身、最近実務でBFSを使う機会があり、改めて理解を深めたいと思い整理しました。今回は、よりイメージしやすいように、ECサイトでよくある「商品カテゴリツリー」を題材にしています。
この記事では、

  • BFSの考え方
  • どんな場面で使えるのか(実務例)
  • 実装例(商品カテゴリツリー)

を、初学者でも実務者でも分かるように解説していきます。


商品カテゴリのツリー構造とは?

ECサイトでは、商品をカテゴリで分類するのが一般的です。そのカテゴリは次のように**階層構造(ツリー)**になっています:

家電
├── テレビ
│   ├── 液晶テレビ
│   └── 有機ELテレビ
├── 冷蔵庫
└── 洗濯機

この構造をデータで持つには、カテゴリが親子関係を持つ自己リレーション構造になります。

const categoryTree = {
  id: 1,
  name: "家電",
  children: [
    {
      id: 2,
      name: "テレビ",
      children: [
        { id: 3, name: "液晶テレビ", children: [] },
        { id: 4, name: "有機ELテレビ", children: [] }
      ]
    },
    { id: 5, name: "冷蔵庫", children: [] },
    { id: 6, name: "洗濯機", children: [] }
  ]
};

BFSとは?

BFS(幅優先探索)は、あるノードの近くにあるものを先に処理してから、遠くのノードを処理する探索方法です。

ツリー構造で言うと:

  • 「親 → 全ての子(同階層) → 全ての孫(次の階層)」の順に探索します

  • 「横に広がるように」見ていくのが特徴です


BFSが必要になる実務シーン

例1: 全カテゴリを「階層順」に表示したい

「親 → 子 → 孫」の順でリストにしたい → BFS!

例2: 特定の階層(例:第2階層)だけ抽出したい

→ BFSならレベル情報を扱える!

例3: 最も近い一致(例:カテゴリ名)を探したい

→ 浅いところから順に探索できるので効率的!


実装してみよう!カテゴリをBFSで並べる

function bfsCategoryListWithLevel(root) {
  const result = [];
  const queue = [{ node: root, level: 0 }];

  while (queue.length > 0) {
    const { node, level } = queue.shift();
    result.push({ name: node.name, level });

    if (node.children) {
      for (const child of node.children) {
        queue.push({ node: child, level: level + 1 });
      }
    }
  }

  return result;
}


console.log(bfsCategoryListWithLevel(categoryTree));
// → [
//     { name: "家電", level: 0 },
//     { name: "テレビ", level: 1 },
//     { name: "冷蔵庫", level: 1 },
//     { name: "洗濯機", level: 1 },
//     { name: "液晶テレビ", level: 2 },
//     { name: "有機ELテレビ", level: 2 }
//   ]

「親 → 全ての子(同階層)→ 全ての孫」の順で並びます。


データベースでもBFS?

実際のECサイトなどでは、カテゴリは次のようなシンプルなテーブル構造で管理されていることが多いです。

CREATE TABLE categories (
  id INT PRIMARY KEY,
  name VARCHAR(255) NOT NULL,
  parent_id INT
);

parent_id が親カテゴリの id を示しており、これによって自己リレーション(親子関係)が構築されます。
この仕組みでツリー構造は表現できますが、SQLの ORDER BY は単純なカラムの並び順(例えば id や name)を決めるものであり、parent_id に基づく階層順(親→子→孫)には並びません。

そのため、実務では以下のような手順でカテゴリの階層順処理を行います:

  1. データベースからカテゴリを全件取得する(id / parent_id 形式のフラットデータ)

  2. アプリケーション側で必要に応じてツリー構造に組み立てる

  3. ツリー構造またはフラットデータをBFSで親から順に探索・並び替える

こうすることで、UI上で自然な階層順のリスト表示やメニュー展開が可能になります。


BFSとORDER BYの違いは?

比較 BFS ORDER BY
並び方 親→子→孫(階層順) 値順(名前順、ID順)
目的 階層表示・UI順序 並び替え表示・一覧表示
必要な情報 parentId(自己リレーション) 並びたいカラムだけ

まとめ

ポイント 内容
BFSとは? ツリー構造を横に広がる順に探索する手法
実務で使う場面 カテゴリ表示、階層メニュー、浅い順の検索など
実装方法 JavaScriptでキュー(Queue)を使って処理
データ構造 同じCategoryモデルの自己リレーションでOK

株式会社シンシア

株式会社シンシアでは、実務未経験のエンジニアの方や学生エンジニアインターンを採用し一緒に働いています。
※ シンシアにおける働き方の様子はこちら

シンシアでは、年間100人程度の実務未経験の方が応募し技術面接を受けます。
その経験を通し、実務未経験者の方にぜひ身につけて欲しい技術力(文法)をここでは紹介していきます。

13
7
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
13
7

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?