web-dev-qa-db-ja.com

ブール値フィールドのインデックス付けにパフォーマンスの向上はありますか?

_WHERE isok=1_を含むクエリを作成しようとしています。名前が示すように、isokはブールフィールドです(実際には、必要に応じて0または1に設定されるTINYINT(1) UNSIGNED)。

このフィールドのインデックス作成でパフォーマンスが向上しますか?エンジン(この場合はInnoDB)は、インデックスの検索のパフォーマンスを向上させるのでしょうか、それとも悪化させるのでしょうか?

83

あんまり。あなたはそれを本のように考えるべきです。ブックに3種類の単語しかない場合、それらすべてをインデックスに登録すると、インデックスページの数は通常のページと同じになります。

1つの値のレコードが比較的少ない場合、パフォーマンスが向上します。たとえば、1000個のレコードがあり、そのうちの10個がTRUEである場合、isok = 1で検索すると便利です。

Michael Durrantが述べたように、書き込みも遅くなります。

編集:可能な重複: ブール値フィールドのインデックス付け

ここでは、インデックスがある場合でも、レコードが多すぎる場合はインデックスを使用しないと説明しています。 MySQLはチェック時にインデックスを使用しない= 1、ただし= 0で使用する

60
Michael Koper

私の経験では、このような質問を見る人は私たちと同じボートにいるので、ブールフィールドのインデックス付けは無意味であると聞いているので...

約400万行のテーブルがあり、一度に約1000程度しかブールスイッチにフラグが付けられていないので、それが検索対象です。ブール型フィールドにインデックスを追加すると、クエリが大幅に高速化され、約9秒から数分の一秒になりました。

89
oucil

実際のクエリと、インデックス/クエリの組み合わせの選択性に依存します。

ケースA:条件WHERE isok = 1およびその他の条件:

SELECT *
FROM tableX
WHERE isok = 1
  • インデックスが十分に選択的である場合(たとえば、1M行があり、1kのみにisok = 1がある場合)、SQLエンジンはおそらくインデックスを使用になり、それがない場合よりも高速になります。

  • インデックスが十分に選択的でない場合(たとえば、1M行があり、100k以上がisok = 1を持つ場合)、SQLエンジンはおそらくインデックスを使用しないになり、テーブルスキャンを実行します。

ケースB:条件WHERE isok = 1など:

SELECT *
FROM tableX
WHERE isok = 1
  AND another_column = 17

次に、それはあなたが持っている他のインデックスに依存します。 another_columnのインデックスは、おそらく2つの値しか持たないisokのインデックスよりも選択的です。 (another_column, isok)または(isok, another_column)のインデックスはさらに良いでしょう。

22
ypercubeᵀᴹ

いいえ、通常はありません。

通常、選択性/カーディナリティが高い場合、検索用のフィールドにインデックスを付けます。ブール型フィールドのカーディナリティは、ほとんどのテーブルで非常に低くなっています。また、書き込みが少し遅くなります。

6
Michael Durrant

はい、インデックスはパフォーマンスを改善します。インデックスありとなしでEXPLAINの出力を確認します。

ドキュメントから:

インデックスは、特定の列の値を持つ行をすばやく見つけるために使用されます。インデックスがない場合、MySQLは最初の行から開始して、テーブル全体を読み取って関連する行を見つける必要があります。テーブルが大きいほど、コストがかかります。テーブルに問題の列のインデックスがある場合、MySQLはすべてのデータを確認することなく、データファイルの中央でシークする位置をすばやく決定できます。

この場合、インデックスが[〜#〜] decrease [〜#〜]を実行しないと言っても安全だと思うので、そこから得るだけです。

4
ilanco

データの分布に依存します。

1000個の密接に入力されたページがある本を想像してください。私の本の単語は「はい」と「いいえ」だけで、繰り返し繰り返され、ランダムに配布されました。 「はい」のすべてのインスタンスを丸で囲むように求められた場合、本の裏にある索引が役立ちますか?場合によります。

Yesとnoのランダムな分布が半々あった場合、インデックスを検索しても役に立ちません。インデックスは本をより大きくしますが、とにかく最初から始めて、各項目を検索するのではなく、「はい」のすべてのインスタンスを検索し、それらを巡回するように各ページを処理する方が速くなりますインデックスを作成し、インデックスエントリから参照するページへの参照を取得します。

しかし、たとえば、私の1000ページの本に「はい」のインスタンスが10個だけあり、他のすべてが数百万のノーのものだった場合、インデックスは「イエス」のそれらの10個のインスタンスを見つけてそれらを巡回する時間を節約します。

データベースでも同じです。 50:50の分布の場合、インデックスは役に立たない-データベースエンジンは、最初から最後までデータを処理するだけ(フルテーブルスキャン)であり、インデックスはデータベースを大きくするだけです。書き込みと更新が遅くなります。しかし、4000:1の分布(このスレッドのoucilのようなもの)の場合、インデックスシークは、探している4000アイテムに1アイテムであれば、非常に高速化できます。 。

4
Jinlye

実際、これは実行するクエリに依存します。しかし、一般的にははい、他のタイプのフィールドのインデックス付けも同様です。

3
Maksym Polshcha