カテゴリ: Laravel 更新日: 2026/09/02

LaravelでEloquentのリレーションを扱う!withとloadで関連データを取得する方法

LaravelでEloquentを使ってリレーション先のデータを取得する方法(with, load)
LaravelでEloquentを使ってリレーション先のデータを取得する方法(with, load)

先生と生徒の会話形式で理解しよう

生徒

「Laravelでデータベースの関連データを一緒に取り出したいんですが、どうすればいいですか?」

先生

「Eloquent ORMを使えば、リレーションを簡単に扱えます。そのときに便利なのがwithとloadです。」

生徒

「withとloadって、どう違うんですか?」

先生

「それでは、一緒に基本的な使い方を見ていきましょう!」

1. Eloquentのリレーションとは?初心者でもわかる基本概念

1. Eloquentのリレーションとは?初心者でもわかる基本概念
1. Eloquentのリレーションとは?初心者でもわかる基本概念

LaravelのEloquent ORM(エロクアント ORM)は、データベースの複雑なテーブル同士のつながり(リレーション)を、まるでPHPのオブジェクトを操作するかのように直感的に扱える強力な仕組みです。

プログラミング未経験の方でもイメージしやすいように、身近な「ブログ」を例に考えてみましょう。ブログには「記事(Post)」があり、その記事に対して読者が「コメント(Comment)」を投稿します。このとき、1つの記事に対して複数のコメントが紐づくという関係性が生まれます。これを専門用語で「1対多」のリレーションと呼びます。

もしリレーションを使わずにこれらを表示しようとすると、SQLという難しいデータベース言語を自分で細かく書かなければなりませんが、Eloquentなら以下のようなシンプルなコードでデータを取得できます。


// モデルを使って「IDが1の記事」を取得
$post = Post::find(1);

// その記事に紐づく「コメント」をリレーションで取得
$comments = $post->comments;

foreach ($comments as $comment) {
    echo $comment->content;
}

なるほど、よくわかりました!
とても参考になる記事ですね。
Laravelの学習を頑張ります!

このように、Eloquentのリレーションを理解することで、データベースの構造を意識しすぎることなく、「記事を取得するついでに関連するコメントも持ってくる」といった高度な処理を、誰でも読みやすいコードでスムーズに実装できるようになります。これが、Laravelが開発者に愛される大きな理由の一つです。

2. withメソッドで関連データをまとめて取得(Eager Loading)

2. withメソッドで関連データをまとめて取得(Eager Loading)
2. withメソッドで関連データをまとめて取得(Eager Loading)

Laravelでデータベースを操作する際、最も気をつけたいのが「何度もデータベースに問い合わせをして、表示速度を遅くしてしまうこと」です。これを防ぐための強力な武器がwithメソッドです。

通常、記事一覧を表示した後に「それぞれの記事のコメント」を取得しようとすると、記事の数だけデータベースに命令を送ってしまいます。しかし、withを使うことで、最初の1回で「記事」と「それに紐づくコメント」をセットでまとめて取得できます。これを専門用語でeager loading(イーガーローディング)と呼びます。

初心者向けポイント:「買い物」に例えると、卵が必要になるたびに何度もスーパーへ往復するのが通常の動き(N+1問題)、最初に買い物リストを作って一度に全部買ってくるのがwithのイメージです!


// 記事(Post)を取得するタイミングで、関連するコメント(comments)も一緒に読み込む
$posts = Post::with('comments')->get();

// あとは普通にループで表示するだけ!
foreach ($posts as $post) {
    echo "【タイトル】" . $post->title . "<br>";
    
    // ここでコメントを表示しても、追加のデータベースアクセスは発生しません
    foreach ($post->comments as $comment) {
        echo " └ コメント内容:" . $comment->content . "<br>";
    }
}

【タイトル】Laravel学習日記
 └ コメント内容:とても分かりやすいです!
 └ コメント内容:勉強になります。
【タイトル】PHPの基礎について
 └ コメント内容:初心者にもおすすめですね。

このコードの素晴らしい点は、記事が100件、1000件と増えても、データベースへのアクセス回数が最小限(基本2回)で済むことです。Webサイトの読み込みスピードはGoogleの評価(SEO)にも直結するため、関連データを扱うときは必ずwithを使う癖をつけておきましょう。

3. loadで後から関連データを取得する方法(遅延Eagerロード)

3. loadで後から関連データを取得する方法(遅延Eagerロード)
3. loadで後から関連データを取得する方法(遅延Eagerロード)

Laravelのloadメソッドは、すでに取得済みのデータに対して、後から必要なタイミングで関連する情報を付け加える「遅延Eagerロード」という仕組みです。 プログラミングの世界では、最初からすべてのデータを詰め込むのではなく、「必要になった瞬間に、必要な分だけ追加で持ってくる」という賢い使い分けが重要になります。

例えば、SNSの投稿アプリを想像してみてください。タイムラインを表示する時点では「投稿本文」だけあれば十分ですが、特定の投稿をクリックして詳細画面を開いたときだけ「その投稿に付いたコメント」を表示したい、といった場面でこのloadが真価を発揮します。

具体的な活用サンプル

// 1. まずは「記事」だけを1件取得する
$post = Post::first();

// この時点では、まだコメントのデータはデータベースから取得していません。
// 2. 「やっぱりコメントも表示したい」となったタイミングで後出しで読み込む
$post->load('comments');

// これで、$postの中にコメント情報が補充されました。
foreach ($post->comments as $comment) {
    echo $comment->content;
}
実行結果のイメージ

なるほど、わかりやすいですね!
Laravelの勉強がんばりましょう。
エンジニアへの第一歩です。

もしloadを使わずに、ループの中で何度も$post->commentsを呼び出すと、その回数分だけデータベースへ問い合わせが発生してしまい、動作が重くなる原因(N+1問題)になります。 しかし、この方法なら「必要なときに1回だけ」まとめてデータを取得できるため、初心者の方でも効率的で読みやすいコードを書くことができます。

4. with(Eagerロード)とload(Lazy Eagerロード)の使い分け

4. with(Eagerロード)とload(Lazy Eagerロード)の使い分け
4. with(Eagerロード)とload(Lazy Eagerロード)の使い分け

Laravelで効率的なデータ取得を行う際、withとloadのどちらを使うべきか迷うことがあります。結論から言うと、「データを読み込むタイミング」で使い分けるのが正解です。

  • 最初から関連データが必要なとき(事前読み込み) → with
  • 条件によって後から読み込みたいとき(後追い読み込み) → load

初心者向けの具体例:ブログシステムで解説

たとえば、「記事(Post)」とその「投稿者(User)」のデータを表示する場合を考えてみましょう。

① 最初からセットで取得する「with」

一覧画面など、最初から「記事と一緒に投稿者名も絶対に表示する」と決まっている場合は、withを使います。これで、データベースへの問い合わせ回数を最小限に抑えられます(N+1問題の防止)。


// 記事を取得する「ついでに」投稿者データも持ってきて!と指示
$posts = Post::with('user')->get();

foreach ($posts as $post) {
    echo $post->user->name; // すでにデータがあるのでスムーズに表示
}

② 必要なときだけ後で取得する「load」

一方で、特定の条件を満たしたときだけ関連データが必要になる場合は、一度取得した変数に対してloadを実行します。


// まずは記事だけを取得
$posts = Post::all();

if ($viewFullDetails) {
    // 詳細を表示する場合のみ、あとから投稿者データを追加で読み込む
    $posts->load('user');
}

このように、「コントローラーの最初で準備しておくならwith」、「ロジックの途中で必要になったらload」と覚えるのが、パフォーマンス最適化の第一歩です。この使い分けを徹底するだけで、アプリの動作速度は劇的に改善されます。

5. 複数のリレーションを同時に取得する

5. 複数のリレーションを同時に取得する
5. 複数のリレーションを同時に取得する

Eloquentでは、withやloadで複数のリレーションを同時に指定することもできます。例えば、記事とコメント、さらにコメントを書いたユーザー情報を一度に取得することが可能です。


$posts = Post::with(['comments', 'user'])->get();

このように書けば、記事を取得すると同時に「記事を書いたユーザー情報」と「コメント」も取得できるので、ビュー(画面表示)でまとめて扱うことができます。

6. リレーション取得を使うメリット

6. リレーション取得を使うメリット
6. リレーション取得を使うメリット

リレーション先のデータをwithやloadで取得するメリットは大きく分けて2つあります。

  1. パフォーマンスの向上:データベースへの無駄なアクセスを減らし、アプリケーションの動作を軽くできます。
  2. コードのシンプル化:複雑なSQLを書かずに、オブジェクトとして自然に関連データを扱えるので、初心者でも直感的に理解できます。

特に大規模なアプリケーションになると、リレーションを正しく使うかどうかで処理速度や可読性に大きな差が出ます。

まとめ

まとめ
まとめ

ここまで、LaravelのEloquent ORMにおける重要な機能である「リレーションの取得方法」について詳しく解説してきました。Webアプリケーション開発において、データベースから効率的にデータを取得することは、サービスのパフォーマンスを左右する非常に重要な要素です。

特に「N+1問題」と呼ばれる、ループの中でクエリが大量に発行されてしまう現象は、初心者が最も陥りやすい罠の一つです。今回学んだwithメソッドによるイーガーローディング(Eager Loading)を活用すれば、この問題をスマートに解決できます。

リレーション取得のポイントをおさらい

Eloquentのリレーションを使いこなすために、以下の3つのポイントを意識しましょう。

  • クエリの最適化: withを使うことで、1回のクエリで必要なデータをすべて取得し、データベースへの負荷を最小限に抑えることができます。
  • 柔軟なデータ操作: 既に取得済みのインスタンスに対して、必要になったタイミングでデータを追加するloadメソッドを使い分けることで、メモリ消費を抑えた設計が可能になります。
  • 多重リレーションの活用: ドット記法(例:with('comments.user'))を使うことで、リレーションのその先にあるデータまで一気に取得できるため、複雑なデータ構造も直感的に扱えます。

実践的なサンプルコード:条件付きイーガーローディング

実際の開発現場では、「関連データをただ取得するだけでなく、特定の条件で絞り込みたい」というケースがよくあります。その場合は、withの中にクロージャを渡すことで対応可能です。


// 「承認済み」のコメントだけを一緒に取得する例
$posts = Post::with(['comments' => function ($query) {
    $query->where('status', 'approved');
}])->get();

foreach ($posts as $post) {
    echo "記事タイトル: " . $post->title;
    foreach ($post->comments as $comment) {
        echo "承認済みコメント: " . $comment->content;
    }
}

このように、Laravelのリレーション機能は非常に強力です。単純なデータ取得にとどまらず、ビジネスロジックに合わせた柔軟なデータの取り出し方をマスターすることで、より高度なPHPプログラミングが可能になります。

パフォーマンスを意識した設計

リレーションを多用すると、ついつい「何でもかんでもwithで取ってしまえば楽だ」と考えがちですが、データ量が多い場合は注意が必要です。必要なカラムだけを指定して取得する(例:with('user:id,name'))といったテクニックも併せて覚えておくと、メモリの節約になり、さらにワンランク上のエンジニアを目指せます。

今回学んだ基礎を土台にして、実際のプロジェクトでリレーションを定義し、データの関連付けを意識したコーディングに挑戦してみてください。Eloquentの便利さを実感できるはずです。

先生と生徒の振り返り会話

生徒

「先生、ありがとうございました!withとloadの違いがスッキリ分かりました。特に『N+1問題』を防ぐためにwithが重要だっていうのが一番の驚きでした。」

先生

「それは良かったです。最初はあまり意識しなくても動いてしまうのがLaravelの良いところでもあり、怖いところでもあるんです。大量のデータを扱うようになると、その一歩進んだ理解がアプリの快適さを決めるんですよ。」

生徒

「さっきのサンプルコードにあった、条件付きでリレーションを取得する方法も便利そうですね。例えば『非公開のコメントは表示しない』みたいな処理がコントローラーで完結するのは助かります。」

先生

「その通りです!ビューの中でif文をたくさん書くよりも、Eloquentの段階でデータを整えておくのがスマートな設計ですね。ちなみに、リレーション先がさらにリレーションを持っている場合、例えば『投稿のコメントの投稿者』はどうやって取得するか分かりますか?」

生徒

「ええと、たしかドット記法でつなげればいいんですよね?Post::with('comments.user')みたいな感じで!」

先生

「大正解!その調子です。Eloquentは深掘りすればするほど便利な機能が出てきます。まずはこのwithとloadを自由に使いこなせるようになって、データベース操作のマスターを目指しましょう。次は、多対多のリレーションについても学習してみると、さらに世界が広がりますよ。」

生徒

「はい!どんどんコードを書いて慣れていこうと思います。ありがとうございました!」

カテゴリの一覧へ
新着記事
New1
Symfony
Symfonyとは?PHPの堅牢なフレームワークの特徴と活用シーン
New2
Laravel
Laravelのプロジェクト構造を理解しよう!初心者向けディレクトリ解説
New3
Laravel
Laravelのモック化を完全解説!MockeryとFacadesでテストを簡単にする方法
New4
CodeIgniter
CodeIgniterバリデーションのよくある失敗例と対策!初心者向けエラーチェック完全ガイド
人気記事
No.1
Java&Spring記事人気No1
Symfony
Symfonyの抽象コントローラとは?AbstractControllerを初心者向けにやさしく解説
No.2
Java&Spring記事人気No2
PHP
PHPで定数を定義する方法!defineとconstの違いと使い分けを徹底比較
No.3
Java&Spring記事人気No3
Symfony
Symfonyでバリデーションメッセージを多言語対応する方法!初心者でもわかる国際化の基本
No.4
Java&Spring記事人気No4
Laravel
LaravelのBlade構文まとめ!@if @foreach など基本ディレクティブ解説
No.5
Java&Spring記事人気No5
Laravel
Laravelでログを出力する方法(Monolog・storage/logs)
No.6
Java&Spring記事人気No6
Laravel
Laravelのインストール方法まとめ!ComposerとLaravel Installerの使い方
No.7
Java&Spring記事人気No7
Laravel
Laravelのルーティングの基本構文と書き方をやさしく解説!初心者でも理解できるWebルートの仕組み
No.8
Java&Spring記事人気No8
Symfony
Symfonyでルーティングとコントローラを連携する方法をやさしく解説!初心者でもわかるURLと処理のつなげ方