1. 复现问题
慢查询的出现是常态还是偶尔?是否在业务允许范围内?
"不要过早优化,先 Make it work / right,再 Make it fast。"
建议先将查询语句及其触发条件记录下来,便于后续测试、分析和对比。
2. 定位问题
2.1 单机数据库: explain
查询执行计划
数据库默认优化后的执行计划是否使用了合适的索引、是否走了全表扫描、排序是否使用了临时表等。然后我们可以进行一些手动优化。
2.2 分布式场景: 尾部延迟放大
任务分片后,部分节点可能由于数据倾斜、垃圾收集、网络丢包等各种原因导致“尾部慢任务”,拖累整体响应时间。这也要结合业务场景进行适当优化。DDIA中第三章有详细介绍。
3. 索引
索引未命中是常见的慢查询原因,当然前提是得有个索引。如果数据库还没有索引,就赶紧建立一个来加速读取吧。
3.1 加索引
索引背后的大致思想是:通过保存一下额外的“路标”,从而帮助你加速找到想要的数据。
索引是额外衍生的数据,它不会干扰数据系统本身的内容,只会影响查询的性能。
然鹅,索引不是越多越好。维护这些索引数据会产生额外的开销,尤其是在写入的时候。如果维护了多份索引,原本仅需一次对主数据的写入,就需要额外再附加多个对于索引的维护操作,造成了写放大,可能会大大影响性能。
另外,我们有各种数据结构可用来保存索引数据,如哈希表、B树族、跳表、红黑树等。尽管做业务的时候大概不需要我们去实现某种索引或是存储引擎,但是了解我们的业务场景与不同数据结构的优劣,并选取其中最合适的那个是相当重要的。
3.2 索引未命中场景与解决方案
LIKE '%xxx'
模糊匹配 → 使用