コース一覧
データベース内部構造:インデックス・トランザクション・分散DB
第1正規形

データベース内部構造:インデックス・トランザクション・分散DB

SQLの書き方ではなく、DBMSの内側を学ぶコースです。RDBとNoSQL、正規化、B-tree、トランザクションとMVCC、クエリプランナ、レプリケーションと分散SQLを通して、性能と整合性の判断根拠を身につけます。

1
データベースの基礎
0. データベースとは8分
1. RDB と NoSQL の違い8分
2. データベースの歴史8分
3. エンティティ関係モデル (ER)8分
4. 主キー・外部キー・候補キー8分
2
正規化
0. 正規化とは何か8分
1. 第1正規形8分
2. 第2正規形8分
3. 第3正規形8分
4. 非正規化のトレードオフ8分
3
インデックスと B-tree
0. インデックスの役割8分
1. B-tree の仕組み8分
2. B+tree(実際の DB 実装)8分
3. ハッシュインデックス8分
4. カバリングインデックス8分
4
トランザクションと ACID
0. トランザクションとは8分
1. ACID 特性8分
2. 分離レベル8分
3. MVCC(マルチバージョン同時実行制御)8分
4. デッドロックと回避8分
5
クエリ最適化
0. クエリプランナの役割8分
1. EXPLAIN の読み方8分
2. Nested Loop / Hash / Merge Join8分
3. インデックスチューニング8分
4. 統計情報とカーディナリティ8分
6
スケーリング
0. レプリケーション8分
1. シャーディング8分
2. CAP 定理8分
3. 結果整合性8分
4. NewSQL と分散 SQL8分

データベース内部構造:インデックス・トランザクション・分散DB

01データベースとは
02RDB と NoSQL の違い
03データベースの歴史
04エンティティ関係モデル (ER)
05主キー・外部キー・候補キー
06正規化とは何か
07第1正規形
08第2正規形
09第3正規形
10非正規化のトレードオフ
11インデックスの役割
12B-tree の仕組み
13B+tree(実際の DB 実装)
14ハッシュインデックス
15カバリングインデックス
16トランザクションとは
17ACID 特性
18分離レベル
19MVCC(マルチバージョン同時実行制御)
20デッドロックと回避
21クエリプランナの役割
22EXPLAIN の読み方
23Nested Loop / Hash / Merge Join
24インデックスチューニング
25統計情報とカーディナリティ
26レプリケーション
27シャーディング
28CAP 定理
29結果整合性
30NewSQL と分散 SQL

データベース内部構造:インデックス・トランザクション・分散DB

第1正規形

カンマ区切りにした列は、二度と検索できない

利用者の電話番号を 1 つの列に入れておいて、2 つ目が必要になったのでカンマで区切って足した。よくある成り行きです。

利用者 ID氏名電話番号
1佐藤090-1111-1111, 080-2222-2222
2鈴木070-3333-3333

しばらくは動きます。表示するだけなら、そのまま画面に出せば済むからです。

崩れるのは、その列で何かをしたくなったときです。「080 で始まる番号を持つ人」を探すには、文字列の途中に含まれるかどうかで探すしかありません。この探し方では索引が使えず、必ず全件を読みます。「2 つ目の番号だけ直す」には、何文字目から何文字目かを数える処理が要ります。「番号を 1 本しか持たない人」を数えるには、カンマの個数を数えることになります。

そして、同じ番号が 2 回入っていても、桁数がおかしくても、DB は何も言いません。1 つの列に複数の値が入っている限り、値そのものに制約を掛けられないからです。

入力の側でも守れません。1 本ずつ入力させる画面なら形式を確かめられますが、まとめて 1 つの文字列にしてから保存すると、確かめる場所が消えます。区切り文字を全角で打った 1 件が、そのまま通ります。

別の表に出すと、検索できる形に戻る

直し方は、多値の列を別の表へ移すことです。利用者 1 人につき、番号の数だけ行を作ります。利用者 ID と番号の 2 列だけの、素っ気ない表になります。

こうすると、番号は 1 行 1 値になります。「080 で始まる」は前方一致になるので索引が効き、重複禁止の制約も掛けられ、番号を 1 本消すのは 1 行消すだけになります。

表を分けると、番号そのものにも情報を持たせられます。どれが主に使う番号かを表す列を足す、種別を分ける、登録した順を持たせる。カンマ区切りの文字列には、こうした付随情報を足す場所がありません。増やしたければ区切り文字をもう 1 種類決めるしかなく、そこから収拾がつかなくなります。

元の表に行を増やして、同じ人の氏名を 2 回書く手もありますが、これはやめておきます。今度は氏名が 2 か所に書き写され、名前を変えるときに同じ取りこぼしが起きます。1 つ直したつもりが、別の場所に同じ問題を作っただけになります。

JSON の列は違反なのか

いまの DB は JSON 型を持っています。1 つのセルに構造が入るので、形の上では同じ話に見えます。

判断は用途で分かれます。その中身で検索したり、集計したり、他の表とつないだりするなら、外に出して普通の列にします。API の応答をそのまま控えておく、設定のスナップショットを残す、といった「読み返すだけの付随情報」なら、JSON のままで構いません。関数索引などで部分的に引く手段はありますが、本気で検索するなら普通の表のほうが速く、制約も掛けられます。

配列型を持つ DB もありますが、判断の軸は変わりません。並べて表示するだけなら便利で、その中身で他の表とつなぎたくなった時点で限界が来ます。

住所を 1 本の文字列で持つのも似た話です。表示するだけなら 1 列で十分ですが、市区町村ごとに集計したくなった時点で分ける必要が出ます。粒度の決め方は「その単位で検索するか、更新するか、集計するか」であって、理論上の最小単位まで割ることではありません。

1 つのセルには 1 つの値だけ、という状態が第 1 正規形です。

このレッスンに出てくる用語

意味があいまいなまま進んだ語は、ここから読み直せます。

  • 処理計算や代入を表す長方形
  • applicationJSON 本文を送るときの Content-Type
  • 判断YES/NO 分岐を表す菱形
  • エンドポイント「この URL を叩くとこの機能が動く」入口の住所
  • APIアプリ間でデータをやり取りする窓口
  • 関数処理に名前を付けて再利用できる単位
  • 配列サイズ固定の同型データの集まり
生田 陸人
監修生田 陸人
ゆめさくエンジニア / 現役ソフトウェアエンジニア監修者プロフィールを見る →
編集 ゆめさく編集部·公開 2026/05/27·更新 2026/08/26

関連レッスン

  • 第2正規形

    部分関数従属を排除し複合キーの依存を整理する

  • 第3正規形

    推移関数従属を排除し非キー属性の独立性を確保する

  • 非正規化のトレードオフ

    読み取り性能のために冗長を許容する判断基準を学ぶ

  • インデックスの役割

    全件走査と索引参照の違いを計算量から把握する

分からないところは Tap (AI先生) に質問できます

24 時間いつでも、あなたのレベルに合わせて日本語で答えます。