インデックスショットガン
インデックスを使用するか否かの判断をインデックスを理解しないまま行うと間違った判断をしてしまうというアンチパターン。
以下の3つのようなミスが発生してしまう可能性がある。
- インデックスを全く定義しないか、少ししかインデックスを定義しなくなる
- インデックスを多く定義しすぎるか、役立たないインデックスを定義してしまう
- インデックスを活用しないクエリを実行してしまう
インデックスを全く定義しない
データベースはテーブルのインデックスのデータ構造を更新し、インデックスを用いて適切な行セットを検索できるようにしなければならない。
インデックスの更新によってデータベースにオーバーヘッド(INSERT、DELETE、UPDATEを行っているうちにできる未使用領域のようなもの)が生じる。
オーバーヘッドが無駄なものだという考えからインデックスそのものを排除するということが起こる。
インデックスにはオーバーヘッドを正当化するだけのメリットがあるため一概に排除すべきではない。
通常のアプリケーションの場合、テーブルの更新回数よりテーブルに対するクエリ発行が多いことが一般的である。
インデックスは目的の行を素早く見つけられるメリットがあります。
更新時や削除時にも対象の行を検索するために役立つ。
インデックスを定義していない列で検索をする場合、一致行を検索するためにテーブル全体を検索する必要がある。
インデックスを多く定義しすぎる
インデックスのメリットを得られるのはインデックスを使用するクエリを実行するときである。
使用されていないインデックスを作成するメリットはありません。
どのインデックスがどんなクエリに役立つかわからないためテーブルの複数列や列の組み合わせに対してインデックスを定義する場合がある。
使用しない列に対してインデックスを定義した場合、メリットを得られずにオーバーヘッドを増やす要因となる。
インデックスが役に立たない場合
パターン1
user_id(PK) | last_name | first_name |
---|
user_idに対してインデックスを貼る場合、この列はPKは設定されており自動的にインデックスが生成されるため無駄となる。
パターン2
user_id | last_name | first_name |
---|
上記のように苗字と名前列があった際、この2列に対して複合インデックスを貼った場合、左側の列から絞り込まれるためfirst_nameに対してインデックスを貼ることは無駄になる。
パターン3
LIKE述語は前方一致検索でのみインデックスが有効となる。
そのため、部分一致検索の場合はインデックスは無駄となる。
アンチパターンの見つけ方
アンチパターンの名前にもなっている通り、ショットガンのようにむやみやたらにインデックスを作成している場合は注意が必要。
次のような言葉を耳にしたらアンチパターンの兆候であると言える。
「このクエリを高速化するにはどうしたら良い??」
→ テーブルの説明、インデックス、データ量、パフォーマンスの測定、最適化などについて詳細がないため、そういった部分を考慮しない回答はあてずっぽうにしかならず、とりあえずインデックスをつけるなどのアンチパターンに陥る可能性がある
「フィールド全部にインデックスを定義したのに、実行速度が速くならない」
→インデックスが役に立たない場合で説明したが不要なインデックスを付与しても意味がない。
オーバーヘッドを増やす要因となる。
「データベースを遅くすると聞いたためインデックスを使用していない」
→インデックスをうまく使うことでパフォーマンスの改善を期待できる。
アンチパターンを用いても良い場合
ない。
作成することでメリットを得られるはずのインデックスを使用していない場合や、インデックスを作成したが不要になった場合などがあるため十分な情報に基づいて検討をすべき。