運行以下SQL語句之後,您會看到,在第一個ALTER TABLE
語句已運行後,MySQL自動爲tag_id
列創建了非唯一索引question_tag_tag_id_tag_id
。MySQL忘記了爲外鍵自動創建索引?
但第二ALTER TABLE
語句運行後,我覺得MySQL也應該自動對我question_id
列上創建一個非唯一索引question_tag_question_id_question_id
。
但是,從SHOW INDEXES
語句輸出中可以看到,它不在那裏。
爲什麼MySQL忘記第二個ALTER TABLE
聲明?
順便說一句,因爲我已經創建由都question_id
和tag_id
列使用的唯一索引question_id_tag_id_idx
。爲每個人創建一個單獨的索引是多餘的?
mysql> DROP DATABASE mydatabase;
Query OK, 1 row affected (0.00 sec)
mysql> CREATE DATABASE mydatabase;
Query OK, 1 row affected (0.00 sec)
mysql> USE mydatabase;
Database changed
mysql> CREATE TABLE question (id BIGINT AUTO_INCREMENT, html TEXT, PRIMARY KEY(id)) ENGINE = INNODB;
Query OK, 0 rows affected (0.05 sec)
mysql> CREATE TABLE tag (id BIGINT AUTO_INCREMENT, name VARCHAR(10) NOT NULL, UNIQUE INDEX name_idx (name), PRIMARY KEY(id)) ENGINE = INNODB;
Query OK, 0 rows affected (0.05 sec)
mysql> CREATE TABLE question_tag (question_id BIGINT, tag_id BIGINT, UNIQUE INDEX question_id_tag_id_idx (question_id, tag_id), PRIMARY KEY(question_id, tag_id)) ENGINE = INNODB;
Query OK, 0 rows affected (0.00 sec)
mysql> ALTER TABLE question_tag ADD CONSTRAINT question_tag_tag_id_tag_id FOREIGN KEY (tag_id) REFERENCES tag(id);
Query OK, 0 rows affected (0.10 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> ALTER TABLE question_tag ADD CONSTRAINT question_tag_question_id_question_id FOREIGN KEY (question_id) REFERENCES question(id);
Query OK, 0 rows affected (0.13 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> SHOW INDEXES FROM question_tag;
+--------------+------------+----------------------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+
| Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment |
+--------------+------------+----------------------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+
| question_tag | 0 | PRIMARY | 1 | question_id | A | 0 | NULL | NULL | | BTREE | |
| question_tag | 0 | PRIMARY | 2 | tag_id | A | 0 | NULL | NULL | | BTREE | |
| question_tag | 0 | question_id_tag_id_idx | 1 | question_id | A | 0 | NULL | NULL | | BTREE | |
| question_tag | 0 | question_id_tag_id_idx | 2 | tag_id | A | 0 | NULL | NULL | | BTREE | |
| question_tag | 1 | question_tag_tag_id_tag_id | 1 | tag_id | A | 0 | NULL | NULL | | BTREE | |
+--------------+------------+----------------------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+
5 rows in set (0.01 sec)
mysql>
我明白了,這意味着我不必創建'question_id_tag_id_idx'索引,因爲'question_id'列是聚簇索引中最左邊的前綴模式之一,它已經可以用來查找' question_tag'表格由一個問題ID快速。但'tag_id'列沒有,這就是爲什麼它需要一個單獨的索引來快速查找'question_tag'表中的標籤ID。它是否正確? – bobo 2010-03-12 01:48:45
@bobo'question_id_tag_id_idx'不需要,因爲它只是重複主鍵。 'tag_id'需要單獨的索引,因爲它不會出現在'question_id_tag_id_idx'索引或主鍵的開頭。 – 2010-03-12 10:04:49