主键(Primary Key):唯一标识一条记录,不能有重复,不允许为空。
外键(Foreign Key):表的外键是另一表的主键, 外键可以有重复, 可以是空值。
唯一键( Unique Key):唯一标识一条记录,不能有重复,可以为空。
外键(Foreign Key):表的外键是另一表的主键, 外键可以有重复, 可以是空值。
唯一键( Unique Key):唯一标识一条记录,不能有重复,可以为空。
索引(Index):该字段可以有重复值记录,可以有空值,如果是唯一索引,那么就不可以有重复的记录,可以有空值。
MySQL 中Index 与Key 的区别
Key即键值,是关系模型理论中的一部份,比如有主键(Primary Key),外键(Foreign Key)等,用于数据完整性检否与唯一性约束等。而Index则处于实现层面,比如可以对表个的任意列建立索引,那么当建立索引的列处于SQL语句中的Where条件中时,就可以得到快速的数据定位,从而快速检索。至于Unique Index,则只是属于Index中的一种而已,建立了Unique Index表示此列数据不可重复,猜想MySQL对Unique Index类型的索引可以做进一步特殊优化吧。
于是乎,在设计表的时候,Key只是要处于模型层面的,而当需要进行查询优化,则对相关列建立索引即可。
另外,在MySQL中,对于一个Primary Key的列,MySQL已经自动对其建立了Unique Index,无需重复再在上面建立索引了。
作用:
主键:用来保证数据完整性。
外键:用来和其他表建立联系,以保证数据的一致性和级联操作。
唯一键:用来用防止数据插入的时候重复。
索引:是提高查询排序的速度。
个数:
主键:一个表只能有一个列是主键。
外键:一个表可以有多个列是外键。
唯一键:一个表可以有多个列是唯一键。
索引:一个表可以有多个列是索引。
列子如下:
CREATE TABLE `city_key1` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`Name` char(35) NOT NULL DEFAULT '',
`CountryCode` char(3) NOT NULL DEFAULT '',
`District` char(20) NOT NULL DEFAULT '',
`Population` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`ID`),
KEY `FK_TEST` (`Name`,`CountryCode`)
) ENGINE=InnoDB AUTO_INCREMENT=4080 DEFAULT CHARSET=latin1;
mysql> EXPLAIN select * from city_key1 where CountryCode='ABC';
+----+-------------+-----------+------------+------+---------------+------+---------+------+------+----------+-------------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+-----------+------------+------+---------------+------+---------+------+------+----------+-------------+
| 1 | SIMPLE | city_key1 | NULL | ALL | NULL | NULL | NULL | NULL | 1 | 100 | Using where |
+----+-------------+-----------+------------+------+---------------+------+---------+------+------+----------+-------------+
1 row in set
mysql> EXPLAIN select * from city_key1 where Name='Kabul' and CountryCode='AFG';
+----+-------------+-----------+------------+------+---------------+---------+---------+-------------+------+----------+-------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+-----------+------------+------+---------------+---------+---------+-------------+------+----------+-------+
| 1 | SIMPLE | city_key1 | NULL | ref | FK_TEST | FK_TEST | 38 | const,const | 1 | 100 | NULL |
+----+-------------+-----------+------------+------+---------------+---------+---------+-------------+------+----------+-------+
1 row in set
mysql> EXPLAIN select * from city_key1 where Name='Kabul';
+----+-------------+-----------+------------+------+---------------+---------+---------+-------+------+----------+-------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+-----------+------------+------+---------------+---------+---------+-------+------+----------+-------+
| 1 | SIMPLE | city_key1 | NULL | ref | FK_TEST | FK_TEST | 35 | const | 1 | 100 | NULL |
+----+-------------+-----------+------------+------+---------------+---------+---------+-------+------+----------+-------+
1 row in set
mysql>
最左边前缀(leftmost prefix of the index)——查询必须从索引的最左边的列开始,否则无法使用索引。