なぜMySQL複数列インデックスが過密になっているのですか?
-
13-10-2019 - |
質問
MySQLテーブルをフォローすることを検討してください。
CREATE TABLE `log`
(
`what` enum('add', 'edit', 'remove') CHARACTER SET ascii COLLATE ascii_bin NOT NULL,
`with` int(10) unsigned NOT NULL,
KEY `with_what` (`with`,`what`)
) ENGINE=InnoDB;
INSERT INTO `log` (`what`, `with`) VALUES
('add', 1),
('edit', 1),
('add', 2),
('remove', 2);
私が理解しているように、 with_what
インデックスには、最初に2つの一意のエントリが必要です with
レベルと3(編集:4)ユニークなエントリ what
「subindex」。しかし、MySQLは、各レベルの4つの一意のエントリを報告しています。言い換えれば、各レベルの一意の要素の数は常にの行数に等しくなります log
テーブル。
編集:「第2レベル」がレコードの総数に等しい一意のエントリの数を持つことは問題ありませんが、トップレベルでは大丈夫ではありません。
edit2:占有されているビットの数があるかどうかに気づきました with
たとえば、int(11)に戻り、int(10)に戻るなど、列は変更され、その後、カーディナリティは予想どおりに機能し始めます。平 EXPLAIN SELECT COUNT(DISTINCT 'with') FROM log
適切な値を表示します rows
.
それはバグ、機能、または私の誤解ですか?
解決
SHOW INDEXES
近似の統計を示します。
これらの統計は、テーブルのクエリが実行されると自動的に収集され、さらに、発行することで手動で収集することができます ANALYZE TABLE log
.
Cardinality列の値は正確ではなく、通話の間に変更できます ANALYZE
, 、たとえ基礎となるテーブルが変更されていなくても。
他のヒント
あなたの理解は間違っています。マルチ列キーは、複数の列ではなく、複数の値から作成されます。 MySQLは、4つのユニークなエントリのペアを入力したため、4つの一意のエントリをレポートします。
これらの列の個別のインデックスを説明したので、代わりに
KEY `with_what` (`with`,`what`)
そのはず
KEY `with` (`with`),
KEY `what` (`what`)
そして、それはあなたが望んでいたように機能するはずです。
「マルチ列」インデックスは「連結インデックス」と考える必要があります。つまり、個々の列がインデックスに連結されています。つまり、各行に1つのインデックスエントリがあり、そのエントリにはすべてのインデックス付き列が含まれています。
私の電子ブックを見て、インデックスの仕組みを把握するための全体像を取得してください。 http://use-the-index-luke.com/