mysql性能调优从哪里开始_mysql性能优化步骤解析

1次阅读

mysql性能调优应先分析慢查询日志,确认拖慢系统的sql;再用explain评估执行计划,针对性优化索引;最后根据缓冲池实际命中率和磁盘读频率决定是否调整innodb_buffer_pool_size。

mysql性能调优从哪里开始_mysql性能优化步骤解析

先看慢查询日志,别急着调参数

MySQL性能调优的第一步不是改innodb_buffer_pool_size,也不是加索引,而是确认“到底哪些SQL在拖慢系统”。很多团队一上来就调大缓冲池、换SSD、升级CPU,结果发现90%的延迟来自一条没走索引的select *全表扫描。

实操建议:

  • show variables like 'slow_query_log';确认是否开启;没开就执行set global slow_query_log = 1;
  • long_query_time设为1秒(set global long_query_time = 1;),比默认10秒更早暴露问题
  • 日志输出建议设为FILEset global log_output = 'FILE';),避免写入mysql.slow_log表带来额外开销
  • mysqldumpslow -s t -t 10 /var/lib/mysql/slow.log快速找出耗时TOP10的SQL

用EXPLAIN看执行计划,而不是猜索引有没有用

看到慢SQL后,别直接建索引。先跑一遍EXPLAIN,否则极容易建错索引——比如给WHERE a = ? AND b IN (?, ?) ORDER BY c建了(a)单列索引,实际需要的是(a, b, c)联合索引。

重点关注三项:

  • type:从ALL(全表扫描)→ rangerefconst是优化方向;如果还是ALL,说明没走索引或索引失效
  • rows:预估扫描行数,和实际数据量差距过大(比如表有10万行,rows=98234),大概率没利用好索引选择性
  • Extra里出现using filesortUsing temporary,意味着排序/分组没走索引,必须干预

innodb_buffer_pool_size前,先验证内存是否真够用

盲目把innodb_buffer_pool_size设成物理内存70%,可能反而引发OS频繁swap——尤其当服务器还跑着Java应用或redis时。真正该看的是InnoDB缓冲池的“水位”是否健康。

执行SHOW GLOBAL STATUS LIKE 'innodb_buffer_pool_pages_%';后关注两个数字:

  • Innodb_buffer_pool_pages_free ≈ 0?说明缓冲池长期打满,但不等于“足够大”——得结合Innodb_buffer_pool_reads(磁盘读次数)判断:如果该值持续 > 100/秒,说明频繁回磁盘,才真需要扩容
  • Innodb_buffer_pool_read_requests ÷ Innodb_buffer_pool_reads
  • 注意:重启MySQL后pages_free会重置,要等业务流量稳定后再观察

转换MyISAM表到InnoDB时,小心ALTER table ... ENGINE=InnoDB锁表

线上大表执行ALTER TABLE t ENGINE=InnoDB会全程锁表(尤其MySQL 5.6及之前),业务高峰期执行等于主动停服。这不是“要不要转”的问题,而是“怎么转才不伤业务”。

安全做法:

  • 对500MB以上表,优先用pt-online-schema-change(Percona Toolkit),它通过触发器+影子表实现无锁变更
  • 若只能用原生命令,务必在低峰期执行,并提前用SELECT count(*)确认表大小;千万避开mysqldump + DROP + IMPORT这种“先清空再重建”的方式——期间数据完全不可用
  • 转换后检查innodb_file_per_table=1是否生效,否则所有表数据仍挤在ibdata1里,后续无法单独收缩某张表空间

真正的调优起点从来不在配置文件里,而在每条被EXPLAIN戳穿的SQL和每份被mysqldumpslow揪出的慢日志中。最容易被忽略的,其实是“没查慢日志就调参”和“没看rows就建索引”这两件事。

text=ZqhQzanResources