Mysql查询索引优化实例
单表240W+数据,原本的索引没有一个是对的,数据表后来被重构了。sql是这样的:SELECT sum(`reals`) AS dur, uid FROM app_learn WHERE `vtime` > 1527782399 GROUP BY uid ORDER BY dur DESC, 八核16Gmysql运行时间3秒左右,每到早晨10点就cpu100%。
索引sql是这样的 alter table app_learn add index test(vtime,reals),sql运行时间0.1秒左右
简单分析一下,首先是innodb存储引擎,索引指向对主键的引用,故而group by uid这行不用加索引;其次sql只查两个字段,而且两个字段都是int字段,故而order by sum(reals) 可以建索引,触发innodb的索引覆盖;最后是where vtime> 的条件
CREATE TABLE `app_learn` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`uniqueid` bigint(20) NOT NULL DEFAULT '0' COMMENT '唯一id值',
`cid` int(11) DEFAULT '0' COMMENT '分类id',
`uid` int(11) NOT NULL DEFAULT '0' COMMENT '用户id',
`rid` int(11) NOT NULL DEFAULT '0' COMMENT '音频id',
`current` int(11) DEFAULT '0' COMMENT '学习时长',
`reals` int(10) NOT NULL DEFAULT '0' COMMENT '真实学习时长',
`duration` int(11) DEFAULT '0' COMMENT '总时长',
`y` int(4) NOT NULL DEFAULT '0' COMMENT '年',
`m` int(2) NOT NULL DEFAULT '0' COMMENT '月',
`d` int(2) NOT NULL DEFAULT '0' COMMENT '日',
`w` int(5) NOT NULL DEFAULT '0' COMMENT '周',
`h` int(2) DEFAULT '0' COMMENT '小时',
`vtime` int(11) DEFAULT '0' COMMENT '创建时间',
PRIMARY KEY (`id`,`uid`,`rid`,`uniqueid`),
KEY `uniqueid` (`uniqueid`,`uid`,`rid`),
KEY `cid` (`cid`,`uid`),
KEY `cid_2` (`cid`,`rid`),
KEY `uid` (`uid`),
KEY `idx_rid` (`rid`)
) ENGINE=InnoDB AUTO_INCREMENT=2486599 DEFAULT CHARSET=utf8 ROW_FORMAT=DYNAMIC;