独学でシステム開発を覚えてきた人にとって、なかなかきちんと学ぶ機会が少ないのが、データベースの「インデックス」です。

目に見えるSQLやデータ型と違って、なかなかイメージを掴みづらいものだと思います。

この記事では、「インデックスとは何か」を、できる限り簡単にお話します。

インデックスを語る上で欠かせない存在「オプティマイザー」さん

さて、データベースには「オプティマイザー」さんという、ちっちゃいおっさんが住んでいます。

このおっさんは、データベースが命令(SQL)を受けた時に、実際にテーブルのデータを探しに行く作業をする人です(※)。

例えば、「1万人の人間が入ったテーブル」に、こんな命令をするとします。

さておっさんはどうするかというと・・・

武器を持たないおっさんは、1万人全員に、年齢を訪ねて回ります。

この探し方を「フルスキャン」といいます。当然、時間がかかります。

あるいは、こんな命令(SQL)を流してみると、

これまた時間がかかります。

人数が多い場合には、そもそも1万人を整列される場所(メモリ)がないとかの問題で、余計に時間がかかったりします。

これでは困りますね。

オプティマイザーさんの秘密兵器「インデックス」

そこで、おっさんにあらかじめこんな指示をしておきます。

この指示を受けたおっさんは、1册のノートを作り始めます。

こんな感じのノートです。

ノートには、0歳〜100歳までのページがあり、各ページには、該当者のマイナンバー(ID)が書き連ねられています。

律儀にも、10代、20代、といった見出しシールまで貼られています。

さて、このノートを持っているおっさんに、先程と同じ命令を出すとどうなるでしょうか。

おっさんはまず、「20代」の見出しシールを手繰り、25歳のページを開き、そこに書いてある番号を読み上げていきます。

そして、その番号の人だけを連れてきます。

当然、先程とは比べ物にならないくらい、高速です。

このようなノートを「インデックス」といいます。

そして、先程の「みんなの年齢くらい覚えといて!」という指示を出すことを、「(年齢フィールドに)インデックスを貼る」といいます。

このノートさえあれば、「若い順に100人連れてきて!」も秒殺です。

ノートの頭から順に、100人分の番号を読み上げるだけです。

あるいは、「20代の人全員連れてきて!」でも楽勝です。

見出しシールひとつ分のページを、まるっと読み上げるだけですから。

25歳の女性を全員連れてきて!」だとどうでしょうか。

確かにこのノートだけでは完結できませんが、まず25歳のページを読み上げて、集まった人だけに性別を聞けばよいので、このノートさえない場合よりは、遥かに効率的です。

奥が深い、複合インデックス

さて、こんどはおっさんにこんな命令(SQL)を出してみましょう。

このような場合でも、おっさんにあらかじめ、「年齢と誕生日の組合せは把握しておいて!」と指示を出すだけでいいのです。

指示を受けると、おっさんは文句ひとつ言わず、こんなノートを作り始めます。

このように、2種類以上のフィールドをツリー状に整理して作ったノートを、「複合インデックス」といいます。

このノートを持ったおっさんに、先程と同じ命令を下すと、

秒殺です。

このノートの優れているところは、「AB型の人全員連れてきて!」といった命令(SQL)にも対応できることです。

血液型ごとに大見出しで区切られているので、少しページ数は多くなりますが、まとめて番号を読み上げることができます。

ところが、こんな命令を出してみると・・・

なんとおっさんは、ノートを放り出して、再び全員に誕生日を尋ね始めます。

このおっさん、実は「ノートのページを飛び飛びに見ることが苦手」なのです。

同じ「血液型×誕生日ノート」でも、誕生日が大見出しになっていれば対応できますが、血液型が大見出しになっていると、対応できないのです。

いわゆる「インデックスが利いていない」状態です。

このように、複合インデックスを貼る場合には、「どちらを大見出しにするか」が非常に重要になります。

ダメ、ゼッタイ。インデックス濫用。

実は、おっさんには、複数のノートを持たせることができます。

それなら、どんな命令(SQL)にでも対応できるように、ありとあらゆる組合せのノート(インデックス)を用意しておけばいいのでは?と思うかもしれません。

ところが、そこにはひとつ落とし穴があります。

ノートが増えすぎると、新しい人が入るたびに、全てのノートに情報を転記する必要が出てきます。

つまり、インデックスが増えすぎると、INSERTやUPDATEが遅くなります。

よく使うSQLのパターンを考え、必要十分なインデックスを用意する必要があるのです。

おしまい。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です