索引用于快速找出在某个列中有一特定值得行。不使用索引,MySQL必须从第1条记录开始读完整的表,直到找到相关行。表越大查询数据所花费的时间越多。如果表中查询列有一个索引MySQL能快速到达某个位置去搜寻数据文件而不必查看所有数据。
索引是对数据库表中一列或多列的值进行排序的一种结构它们包含着对数据表里所有记录的引用指针。
索引是在存储引擎中实现的,因此,每种存储引擎的索引都不一定完全相同并且每种存储引擎也不一定支持所有索引类型。所有存储引擎支持每个表至少16个索引,总索引长度至少256个字节。MySQL中索引的存储类型有两种:btree和hash,具体和表的存储引擎有关。MyISAM和InnoDB存储引擎只支持btree索引。
索引分类
1.普通索引和唯一索引
普通索引是MySQL中的基本索引类型,允许在定义索引的列中插入重复值和空值。唯一索引,索引列的值必须唯一,但也许有空值。如果是组合索引,列值的组合必须唯一。主键索引是一种特殊的唯一索引,不允许有空值。
2.单列索引和组合索引
单列索引即一个索引只包含单个列,一个表可以有多个单列索引。组合索引指在表的多个字段组合上创建的索引,只有在查询条件使用了这些字段的左边字段时,索引才会被使用。使用组合索引时遵循最左前缀集合。
3.全文索引
全文索引类型为FULLTEXT,在定义索引的列上支持值得全文查找允许在这些索引列中插入重复值和空值。全文索引可以在char、varchar、text类型的列上创建。MySQL只有MyISAM存储引擎支持全文索引。
4.空间索引
空间索引是对空间数据类型的字段建立的索引,MySQL中的空间数据类型有4种,分别是:GEOMETRY、POINT、LINESTRING和POLYGON.MySQL使用SPATIAL关键字进行扩展,使得能够用于创建正规索引类似语法创建空间索引。创建空间索引的列,必须将其声明为NOT NULL,空间索引只能在存储引擎为MyISAM的表中创建。
索引设计原则:
1.索引并非越多越好,一个表中如果有大量索引不仅占用磁盘空间,而且会影响 insert、update、delete等语句的性能因为当表中 的数据更改的同时,索引也会进行调整和更新。
2.避免对经常更新的表进行过多的索引,并且索引中的列尽可能的少。而对经常查询的字段应该创建索引但要避免添加不必要的字 段。
3.数据量小的表最好不要使用索引,由于数据较少,查询花费的时间可能比遍历查询字段还要短,索引可能不会产生优化效果
4.条件表达式中经常用到的不同值较多的列上建立索引,在不同值很少的列上不要建立索引。
5.当唯一性是某种数据本身的特征时指定唯一索引。使用唯一索引能确保定义的列的数据完整性,以提高效率
6.在频繁进行排序或分组的列上建立索引,如果待排序的列有多个可以建立组合索引
创建索引
1.创建表的时候创建索引
语法:create table table_name(
[col_name data_type],
[col_name data_type] ...,
[unique|fulltext|spatial] [index|key] [index_name] (col_name [length],...) [asc|desc]
);
unique、fulltext、spatial分别表示唯一索引、全文索引和空间索引。index和key为同义词用来指定创建索引。length为索引 的长度,只有字符串类型的字段才能指定索引长度。asc或desc指定升序或降序的索引值存储。
1.创建普通索引:create table tb_name(...,index (col_name),...)
2.创建唯一索引:create table tb_name(...,unique index index_name(col_name...),...)
注:在组合索引中,如果列不构成索引最左面的前缀,MySQL不能使用局部索引,即如果组合索引包含的列有(col_1、 col_2、col_3),如果查询的条件有(col_1)、(col_1、col_2)、(col_1、col_2、col_3)时会使用索引。
2.在已经存在的表上创建索引
1.使用alter table 语句
alter table tb_name add [unique|fulltext|spatial] [index|key] [index_name] (col_name [length],...) [asc|desc]
2.使用create index创建索引
create [unique、fulltext、spatial] index index_name on table_name (col_name[length],...) [asc|desc]
删除索引
1.使用alter table
alter table table_name drop index index_name;
2.使用drop index
drop index index_name on table_name;