通过索引来优化MySQL语句
合理的建立索引能够加速数据读取效率,不合理的建立索引反而会拖慢数据库的响应速度。索引越多,更新数据的速度越慢。故而索引要准确,适当。
一、优化含有order by的语句
1、ORDER BY + LIMIT组合的索引优化。形如:
SELECT [column1],[column2],.... FROM [TABLE] ORDER BY [sort] LIMIT [offset],[LIMIT];
这个SQL语句优化比较简单,在[sort]这个栏位上建立索引即可。
2、WHERE + ORDER BY + LIMIT组合的索引优化,形如:
SELECT [column1],[column2],.... FROM [TABLE] WHERE [columnX] = [value] ORDER BY [sort] LIMIT[offset],[LIMIT];
这个MySQL语句,如果你仍然采用第一个例子中建立索引的方法,虽然可以用到索引,但是效率不高。更高效的方法是建立一个联合索引 (columnX,sort)
3、不要再WHERE和ORDER BY的栏位上应用表达式(函数),比如:
SELECT * FROM [table] ORDER BY YEAR(date) LIMIT 0,30;
4、WHERE+ORDER BY多个栏位+LIMIT,比如
SELECT * FROM [table] WHERE uid=1 ORDER x,y LIMIT 0,10;
大家可能是加一个这样的索引(x,y,uid)。但实际上更好的效果是(uid,x,y)。这是由MySQL处理排序的机制造成的。
二、> 及 < 操作符
大于或小于操作符一般不用调整,因为它有索引就会采用索引查找,但有的情况下可以对它进行优化,如一个表有100万记录,一个数值型字段A, 30万记录的A=0,30万记录的A=1,39万记录的A=2,1万记录的A=3。那么执行A>2与A>=3的效果就有很大的区别了,因为 A>2时会先找出为2的记录索引再进行比较,而A>=3时则直接找到=3的记录索引。
LIMIT语句优化
在数据库分页中普遍使用,当数据量很大时,limit语句的响应性能急剧下降,如以下两条SQL语句相差就不是在一个数量级上:
select * from table1 limit 10,10
select * from table1 limit 10000,10
这里采用一种方式,首先获取到offset的id然后直接使用limit size来获取数据。经过测试,性能明显要好于直接使用limit。
1、offset比较小的时候。
select * from table1 limit 10,10
多次运行,时间保持在0.0004-0.0005之间
select * from table1 where id >=(select id From table1 order by id limit 10,1) limit 10
多次运行,时间保持在0.0005-0.0006之间,主要是0.0006
结论:偏移offset较小的时候,直接使用limit较优。这个显然是子查询的原因。
2、offset大的时候。
select * from table1 limit 10000,10
多次运行,时间保持在0.0187左右
select * from table1 where id >=(select vid from table1 order by id limit 10000,1) limit 10
多次运行,时间保持在0.0061左右,只有前者的1/3。可以预计offset越大,后者越优。
存储路径选择
将表与表的索引分离存放。大表所对应的索引通常也比较大。一般来说,索引的数量是随着表记录的数量增加而增加,两者是接近于一个正比例的关系。所以,通常表的记录容量大的时候,索引数量也会很庞大。考虑把表和他的索引分别存储于不同的表空间中,甚至在条件允许的情况下,分别存储于不同的硬盘中。这么做的好处是什么呢?最大的好处是让索引比较容易的获得所需要的连续的存储空间,从而提高输入输入的效率。通俗的说,就是可以提高数据的查询效率。如不这么处理的话,查询大容量的记录的话,数据库可能需要花费30秒;而如此设计的话,就可能把时间缩短为10秒。这是一个很明显的性能改善。