我见过太多团队在数据库出问题的时候手忙脚乱,查个慢查询日志都能翻半天,最后发现是索引没建好。其实数据库优化这事儿,说难也难,说简单也简单,核心就一句话:搞清楚数据是怎么存的,又是怎么被查的。今天我把压箱底的十个方案翻出来,从索引到架构,从上到下捋一遍,你照着做,查询速度翻个几倍不是问题。

第一个方案,也是见效最快的:索引优化。很多人以为建了索引就完事了,大错特错。索引不是越多越好,每多一个索引,写入的时候就要多维护一棵B+树,写性能就掉一截。你要做的第一件事是看慢查询日志,找出那些执行时间超过100毫秒的语句,然后逐个分析执行计划,看看有没有走全表扫描。记住一个原则:区分度高的列放前面,等值查询优先于范围查询。比如一个用户表,性别字段区分度太低了,建索引基本没用,还不如直接扫全表。
第二个方案容易被忽略:查询语句本身的重写。我见过太多人写SQL跟写散文似的,子查询套子查询,UNION一个接一个。实际上,很多子查询都能改写成JOIN,性能能提升好几倍。举个真实案例,之前帮一个电商客户优化订单查询,原来用IN加子查询要花2.3秒,改写成EXISTS关联查询后直接降到40毫秒。还有一点要特别注意,SELECT后面别用星号,只查你需要的字段,这样能减少IO开销和网络传输量。
第三个方案是分区表。当你的表数据量超过千万级,即使有索引,查询性能也会明显下降。这时候就得考虑分区了。分区不是分表,它还是在同一张表里,但物理存储上分成了多个区域。比如订单表可以按月份分区,查询三个月内的订单时,数据库只扫描对应的三个分区,而不是全表。我建议你用RANGE分区,按时间字段来分,这是最常用也最好维护的。但要注意,分区键必须是你查询条件里常用的字段,不然白搭。
第四个方案,缓存层。这是提升查询速度最快的手段,没有之一。Redis现在几乎成了标配,但你得知道缓存什么、怎么缓存。我见过太多人把整个表缓存到Redis里,结果数据一更新就全失效,缓存命中率低得可怜。正确的做法是:缓存那些热点数据,比如首页推荐、热门文章、用户会话信息,设置合理的过期时间,用缓存穿透、缓存击穿、缓存雪崩这三座大山的解决方案来保护你的缓存层。记住,缓存是加速器,不是存储层,别把所有数据都往里面塞。
第五个方案,读写分离。一个主库负责写,几个从库负责读,这是最经典的架构优化方案。但很多人搞错了重点,以为搭个主从复制就完事了。实际上,你要考虑的是:读多写少的业务场景才适合读写分离。如果写操作占了一半以上,读写分离反而增加网络开销。另外,主从延迟是个大坑,刚写入的数据马上读,很可能读不到。这时候就得用强制路由,让这类请求走主库。我的建议是,用中间件来做读写分离,比如MyCat、ShardingSphere,别在应用层手动判断。
第六个方案,数据库连接池调优。这个看起来不起眼,但影响巨大。连接池太小,请求排队等待连接,响应时间飙升;连接池太大,数据库资源被连接耗尽,反而更慢。Druid、HikariCP都是好用的连接池,但参数得调。核心参数就三个:初始连接数、最大等待时间。具体数值根据你的业务并发量来算,一般最大连接数设为CPU核心数的两倍左右,等待时间别超过3秒。还要定期监控连接池的使用情况,看看有没有连接泄漏。
第七个方案,SQL执行计划分析。这个不是一次性工作,而是要常态化。我建议你每两周做一次巡检,把执行计划里出现全表扫描、临时表、filesort的SQL全捞出来,逐个优化。现在MySQL 8.0和PostgreSQL 15以上的版本都有很好的性能分析工具,比如EXPLAIN ANALYZE,能直接告诉你每一步消耗了多少时间。千万别凭感觉优化,数据说话。
第八个方案,架构层面的大招:分库分表。这个方案一听就很吓人,确实,能不用就不用。但当你的单表数据量达到亿级,或者单库的TPS超过几千,你就不得不考虑分片了。分片策略要提前想好,按用户ID哈希分片最均匀,按地域分片逻辑清晰但可能数据倾斜。用ShardingSphere这类中间件来做透明化分片,应用层不用改代码。但分片之后,跨分片的JOIN和聚合查询就麻烦了,所以分片键的选择一定要基于你的核心查询场景。
第九个方案,冷热数据分离。这个方案很多人忽略,但效果极好。比如订单表,三年前的订单基本没人在查了,你可以定期把这些历史数据迁移到归档表,或者放到更便宜的存储上,比如TiDB或者OSS。这样热表数据量小了,查询自然就快了。你得写个定时任务,每天凌晨把超过N天的数据迁移走,用DELETE加INSERT的方式,注意别影响白天的高峰期。
第十个方案,硬件和配置优化。这个放在最后说,是因为它能解决瓶颈,但不能弥补架构缺陷。比如把存储换成NVMe SSD,查询速度确实能快好几倍,但如果你SQL写得稀烂,再快的盘也救不了你。配置方面,InnoDB的缓冲池大小要设为物理内存的70%左右,这是最关键的参数。另外,日志文件大小、刷盘策略也要根据你的数据安全要求来调整。
这十个方案,从简单到复杂,从战术到战略,全给你捋了一遍。但我要提醒你的是,别一上来就搞分库分表,那是最后的大招。大部分业务,做好索引、缓存、读写分离这三板斧,性能就能提升80%以上。数据库优化不是一锤子买卖,它是个持续迭代的过程,你要建立监控体系,收集性能数据,定期回顾优化效果。你可以在评论区告诉我你遇到了什么具体的性能问题,我帮你参谋参谋,到底是该加索引还是该上缓存。记住,没有银弹,只有最适合你业务场景的方案组合。


