600字范文,内容丰富有趣,生活中的好帮手!
600字范文 > 《MySQL tips:查询时 尽量不要对字段进行操作》

《MySQL tips:查询时 尽量不要对字段进行操作》

时间:2021-07-14 12:38:13

相关推荐

《MySQL tips:查询时 尽量不要对字段进行操作》

维护一个交易系统,交易记录表tradelog包含交易流水号(tradeid)、交易员id(operator)、交易时间(t_modified)等字段。

建表语句如下:

create table 'tradelog' ('id' int(11) not null,'tradeid' varchar(32) default null,'operator' int(11) default null,'t_modified' datetime default null,primary key ('id'),key 'tradeid' ('tradeid'),key 't_modified' ('t_modified')) engine = InnoDB default charset = utf8mb4;

假设已经记录了从初到底的所有数据,运营部门有一个需求:统计发生在所有年份中7月份的交易记录总数。

我们可以这样写:

select count(*) from tradelog where month(t_modified) = 7;

t_modified字段上有索引,但是会发现这条语句执行时间特别久,才返回结果。

但是MySQL规定:如果对字段做了函数计算,就不能使用索引。

也就是说:

条件为where t_modified = '-7-1'时,可以用上索引,而改成where month(t_modified) = 7的时候就不行了。

B+树同一层的兄弟节点是有序的,所以可以快速定位。

而当使用了month()函数,传入7时,其实B+树不知道接下来是取子节点还是兄弟节点。

所以说对索引字段做函数操作,优化器无法判断最终的结果是不是有序的,所以就会放弃使用搜索树,只能全部扫描该索引树。所以建议在查询时,尽量不要对字段进行操作

为了能够用上索引的快速定位能力,我们就要把SQL语句改成基于字段本身的范围查询:

select count(*) from tradelog where-> (t_modified >= '-7-1' and t_modified < '-8-1') or-> (t_modified >= '-7-1' and t_modified < '-8-1') or-> (t_modified >= '-7-1' and t_modified < '-8-1');

优化器在对于不改变有序性的函数上,也不会考虑使用索引。比如:对于select * from tradelog where id + 1 = 10000这个SQL语句,

这个+1不会改变有序性,但是优化器还是不能用id索引快速定位到9999这一行。所以需要我们在写SQL语句时,手动改写成where id = 10000 - 1才行。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。