硬件是MySQL性能的基础,需根据业务负载选择合适的配置:
innodb_buffer_pool_size(如96GB内存可支持3-4个实例,32GB内存适合1-2个实例),剩余内存留给操作系统和其他进程。操作系统配置直接影响MySQL的资源利用率:
numa=off关闭,提升内存访问效率。noatime(不记录文件访问时间)、nodiratime(不记录目录访问时间)选项,减少磁盘I/O开销。vm.swappiness:设置为0-10(默认60),降低系统使用交换分区(swap)的概率,避免内存不足导致的性能下降;vm.dirty_background_ratio:设置为5-10,控制脏页(未写入磁盘的缓存数据)的后台刷新阈值;vm.dirty_ratio:设置为dirty_background_ratio的2倍(如10-20),限制脏页的最大比例,避免内存耗尽。/etc/sysctl.conf中的参数,如net.ipv4.tcp_tw_reuse=1(复用TIME_WAIT连接)、net.core.somaxconn=65535(增加监听队列长度),提升网络传输效率。MySQL的配置文件(my.cnf或my.ini)需根据硬件资源和业务需求调整,关键参数如下:
innodb_buffer_pool_size:核心参数,用于缓存InnoDB表的数据和索引,建议设置为物理内存的60%-80%(如16GB内存可设为10GB-12GB),减少磁盘I/O。innodb_log_file_size:重做日志(redo log)大小,建议设置为256MB-512MB(如512MB),平衡性能与数据安全性(更大的日志文件允许更大的事务批量提交)。innodb_log_buffer_size:重做日志缓冲区大小,建议设置为8MB-64MB(如16MB),避免频繁写入磁盘。key_buffer_size:MyISAM索引缓存(MyISAM已不推荐用于OLTP场景,可设为256MB-512MB备用)。table_open_cache:表缓存数量,建议设置为16384-32768,减少表打开/关闭的开销。max_connections:最大连接数,建议设置为1000-2000(根据服务器内存和CPU核心数调整),避免连接数耗尽导致拒绝服务;可通过连接池(如ProxySQL)减少实际连接数。thread_cache_size:线程缓存数量,建议设置为64-256,缓存空闲线程,减少线程创建/销毁的开销。innodb_flush_log_at_trx_commit:控制重做日志的刷新频率,主库设为1(默认,保证数据安全性),从库设为2(提升性能,允许丢失1秒内的数据);若对数据安全性要求极高,可保持1。slow_query_log:开启慢查询日志(设为1),记录执行时间超过long_query_time(建议设为1-2秒)的SQL语句,便于优化。innodb_flush_method:设置为O_DIRECT(默认),绕过操作系统缓存,直接写入磁盘,减少双重缓存的开销;若使用RAID卡带电池备份缓存,可设为O_DIRECT_NO_FSYNC进一步提升性能。query_cache_type:MySQL 5.7+已弃用查询缓存(query cache),建议设为0,避免缓存失效带来的性能损耗。索引是提升查询性能的关键,SQL语句的优化能减少不必要的资源消耗:
WHERE、JOIN、ORDER BY子句中的字段)创建索引,优先选择B+树索引(InnoDB默认索引类型);避免在低重复率(如性别)或过长的字段(如TEXT)上创建索引。INDEX(a,b,c)可优化a=1、a=1 AND b=2、a=1 AND b=2 AND c=3的查询),避免创建冗余索引(如INDEX(a)和INDEX(a,b)重复)。OPTIMIZE TABLE命令整理索引碎片(针对InnoDB表,需重建表);定期使用SHOW INDEX FROM table_name分析索引使用情况,删除未使用的索引。EXPLAIN命令查看执行计划,确认type列为ref或range);避免使用SELECT *,仅选择必要的列,减少数据传输量。INNER JOIN代替子查询(如SELECT a.* FROM a JOIN b ON a.id = b.a_id比SELECT * FROM a WHERE a.id IN (SELECT a_id FROM b)更高效);确保JOIN字段上有索引。LIKE '%value%'(无法使用索引),若需模糊查询,可使用LIKE 'value%'(前缀匹配,可使用索引);减少OR条件的使用(可改用UNION替代)。EXPLAIN SELECT ...查看查询计划,重点关注type(访问类型,如ALL表示全表扫描)、key(使用的索引)、rows(扫描的行数),识别性能瓶颈。合理的表结构设计能减少数据冗余,提升查询效率:
TINYINT代替INT表示性别,VARCHAR(50)代替CHAR(50)表示可变长度字符串);避免使用TEXT、BLOB等大字段(可将大字段分离到单独的表中,通过关联查询获取)。utf8mb4字符集(支持完整的Unicode,如emoji),但需注意其占用更多存储空间(每个字符最多4字节);若无需存储emoji,可使用utf8(每个字符最多3字节)。PARTITION BY RANGE (YEAR(create_time)))将数据分散到多个物理文件中,提升查询和维护效率(如删除旧数据只需删除对应分区)。customer_name字段(冗余),避免每次查询都关联客户表。持续的维护和监控能及时发现并解决性能问题:
slow_query_log=1,long_query_time=1),使用pt-query-digest(Percona Toolkit工具)或mysqldumpslow分析慢查询,找出执行慢的SQL语句并优化。OPTIMIZE TABLE命令整理表的碎片(针对InnoDB表,需执行ALTER TABLE table_name ENGINE=InnoDB),提升数据读取效率;对于频繁更新的表,建议每周优化一次。SHOW INDEX FROM table_name查看user_updates和rows_read,若user_updates远大于rows_read,说明索引未被有效使用),删除冗余索引。当单台服务器无法满足业务需求时,需考虑扩展:
binlog同步数据,提升读性能;可通过ProxySQL实现读写分离(自动将读请求分发到从库,写请求发送到主库)。