MySQL 数据库的优化,你知道有哪些?

Wesley13
• 阅读 361
公众号关注“杰哥的IT之旅”, 
    
    
    
  
     
     
     选择“星标”,重磅干货,第一时间送达!
 
    
    
    
 
    
    
    
  
     
     
     
 
    
    
    

MySQL 数据库的优化,你知道有哪些?

转自:赵栩彬

来源:https://segmentfault.com/a/1190000018631870

前言

数据库优化一方面是找出系统的瓶颈,提高MySQL数据库的整体性能,而另一方面需要合理的结构设计和参数调整,以提高用户的相应速度,同时还要尽可能的节约系统资源,以便让系统提供更大的负荷。

1.优化一览图

MySQL 数据库的优化,你知道有哪些?

2.优化


笔者将优化分为了两大类,软优化和硬优化,软优化一般是操作数据库即可,而硬优化则是操作服务器硬件及参数设置。

2.1 软优化

2.1.1 查询语句优化

  • 1.首先我们可以用EXPLAIN或DESCRIBE(简写:DESC)命令分析一条查询语句的执行信息.

  • 2.例:

    DESC SELECT * FROM user

显示:

MySQL 数据库的优化,你知道有哪些? 其中会显示索引和查询数据读取数据条数等信息.

2.1.2 优化子查询

在MySQL中,尽量使用JOIN来代替子查询.因为子查询需要嵌套查询,嵌套查询时会建立一张临时表,临时表的建立和删除都会有较大的系统开销,而连接查询不会创建临时表,因此效率比嵌套子查询高.

2.1.3 使用索引

索引是提高数据库查询速度最重要的方法之一,关于索引可以参高笔者<MySQL数据库索引>一文,介绍比较详细,此处记录使用索引的三大注意事项:

  • LIKE关键字匹配'%'开头的字符串,不会使用索引.

  • OR关键字的两个字段必须都是用了索引,该查询才会使用索引.

  • 使用多列索引必须满足最左匹配.

2.1.4 分解表

对于字段较多的表,如果某些字段使用频率较低,此时应当,将其分离出来从而形成新的表,

2.1.5 中间表

对于将大量连接查询的表可以创建中间表,从而减少在查询时造成的连接耗时.

2.1.6 增加冗余字段 类似于创建中间表,增加冗余也是为了减少连接查询.

2.1.7 分析表,,检查表,优化表

分析表主要是分析表中关键字的分布,检查表主要是检查表中是否存在错误,优化表主要是消除删除或更新造成的表空间浪费.

  • 1.分析表: 使用 ANALYZE 关键字,如ANALYZE TABLE user;

    MySQL 数据库的优化,你知道有哪些?

  • Op:表示执行的操作.

  • Msg_type:信息类型,有status,info,note,warning,error.

  • Msg_text:显示信息.

  • 2.检查表: 使用 CHECK关键字,如CHECK TABLE user [option]

  • option 只对MyISAM有效,共五个参数值:

  • QUICK:不扫描行,不检查错误的连接.

  • FAST:只检查没有正确关闭的表.

  • CHANGED:只检查上次检查后被更改的表和没被正确关闭的表.

  • MEDIUM:扫描行,以验证被删除的连接是有效的,也可以计算各行关键字校验和.

  • EXTENDED:最全面的的检查,对每行关键字全面查找.

  • 3.优化表:使用OPTIMIZE关键字,如OPTIMIZE [LOCAL|NO_WRITE_TO_BINLOG] TABLE user;

LOCAL|NO_WRITE_TO_BINLOG都是表示不写入日志.,优化表只对VARCHAR,BLOB和TEXT有效,通过OPTIMIZE TABLE语句可以消除文件碎片,在执行过程中会加上只读锁.

2.2 硬优化

2.2.1 硬件三件套

  • 1.配置多核心和频率高的cpu,多核心可以执行多个线程.

  • 2.配置大内存,提高内存,即可提高缓存区容量,因此能减少磁盘I/O时间,从而提高响应速度.

  • 3.配置高速磁盘或合理分布磁盘:高速磁盘提高I/O,分布磁盘能提高并行操作的能力.

2.2.2 优化数据库参数

优化数据库参数可以提高资源利用率,从而提高MySQL服务器性能.MySQL服务的配置参数都在my.cnf或my.ini,下面列出性能影响较大的几个参数.

  • key_buffer_size:索引缓冲区大小

  • table_cache:能同时打开表的个数

  • query_cache_size和query_cache_type:前者是查询缓冲区大小,后者是前面参数的开关,0表示不使用缓冲区,1表示使用缓冲区,但可以在查询中使用SQL_NO_CACHE表示不要使用缓冲区,2表示在查询中明确指出使用缓冲区才用缓冲区,即SQL_CACHE.

  • sort_buffer_size:排序缓冲区

2.2.3 分库分表

因为数据库压力过大,首先一个问题就是高峰期系统性能可能会降低,因为数据库负载过高对性能会有影响。另外一个,压力过大把你的数据库给搞挂了怎么办?所以此时你必须得对系统做分库分表 + 读写分离,也就是把一个库拆分为多个库,部署在多个数据库服务上,这时作为主库承载写入请求。然后每个主库都挂载至少一个从库,由从库来承载读请求。

MySQL 数据库的优化,你知道有哪些?

2.2.4 缓存集群

如果用户量越来越大,此时你可以不停的加机器,比如说系统层面不停加机器,就可以承载更高的并发请求。然后数据库层面如果写入并发越来越高,就扩容加数据库服务器,通过分库分表是可以支持扩容机器的,如果数据库层面的读并发越来越高,就扩容加更多的从库。但是这里有一个很大的问题:数据库其实本身不是用来承载高并发请求的,所以通常来说,数据库单机每秒承载的并发就在几千的数量级,而且数据库使用的机器都是比较高配置,比较昂贵的机器,成本很高。如果你就是简单的不停的加机器,其实是不对的。所以在高并发架构里通常都有缓存这个环节,缓存系统的设计就是为了承载高并发而生。所以单机承载的并发量都在每秒几万,甚至每秒数十万,对高并发的承载能力比数据库系统要高出一到两个数量级。所以你完全可以根据系统的业务特性,对那种写少读多的请求,引入缓存集群。具体来说,就是在写数据库的时候同时写一份数据到缓存集群里,然后用缓存集群来承载大部分的读请求。这样的话,通过缓存集群,就可以用更少的机器资源承载更高的并发。

MySQL 数据库的优化,你知道有哪些?

结语


一个完整而复杂的高并发系统架构中,一定会包含:各种复杂的自研基础架构系统。各种精妙的架构设计.因此一篇小文顶多具有抛砖引玉的效果,但是数据库优化的思想差不多就这些了.

往期资源回顾 需要可自取

    
    
    
 
     
     
     DevOps 实践手册、linux系统诊断、大数据工程师必读手册、OSS运维基础实战手册、程序员面试宝典、深入浅出 Kubernetes 实战手册、RDS数据库入门一本通、CDN排坑指南
 
     
     
     一篇文章带你解读从初级运维工程师到资深运维专家的学习路线
 
     
     
     40+ 张最全 Linux / C / C++ 思维导图!
 
     
     
     学习 Python 的 14 张思维导图!
 
     
     
     7 张思维导图带你掌握 “Python学习路线”
 
     
     
     我花了一周的时间,就为了整理这份 97 页的 Python 自动化系列文档。【附获取方式】
 
     
     
     我精心整理的 136 页 Excel 数据透视表 PDF 文件!【附获取方式】

    
    
    

    
    
    
 
     
     
     
     
     推荐阅读
 
     
     
     
  
      
      
      
   
       
       
       
    
        
        
         
          
           
            
             
              
               
                
                 
                  
                   
                   超经典!十步完全理解 SQL 
                   数据库分库分表解决方案汇总 
                   高性能 MySQL 主从架构的复制原理及配置详解 
                   全面解析 52 条 SQL 语句性能优化策略,建议收藏! 
                   MySQL 高频面试题,都在这了 
                   免费在线 SQL 数据库环境,学习测试两不误! 
                   
                  
                 
                
               
              
             
            
           
          
        
   
       
       
       
  
      
      
      
 
     
     
     

    
    
    

    
    
    
 
     
     
     
  
      
      
      
  
      
      
         
       
       
       
    
        
        
             
         
         
         
      
          
          
          
       
           
           
           
        
            
            
            
         
             
             
             
          
              
              
               
                
                 
                
                
                点个[在看],是对杰哥最大的支持! 
                
              
         
             
             
             
        
            
            
            
       
           
           
           
      
          
          
          
     
         
         
         
   
       
       
       
 
     
     
     

    
    
    

本文分享自微信公众号 - 杰哥的IT之旅(Jake_Internet)。
如有侵权,请联系 support@oschina.cn 删除。
本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一起分享。

点赞
收藏
评论区
推荐文章
blmius blmius
2年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
Jacquelyn38 Jacquelyn38
2年前
2020年前端实用代码段,为你的工作保驾护航
有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
Stella981 Stella981
2年前
Python3:sqlalchemy对mysql数据库操作,非sql语句
Python3:sqlalchemy对mysql数据库操作,非sql语句python3authorlizmdatetime2018020110:00:00coding:utf8'''
Stella981 Stella981
2年前
KVM调整cpu和内存
一.修改kvm虚拟机的配置1、virsheditcentos7找到“memory”和“vcpu”标签,将<namecentos7</name<uuid2220a6d1a36a4fbb8523e078b3dfe795</uuid
Easter79 Easter79
2年前
Twitter的分布式自增ID算法snowflake (Java版)
概述分布式系统中,有一些需要使用全局唯一ID的场景,这种时候为了防止ID冲突可以使用36位的UUID,但是UUID有一些缺点,首先他相对比较长,另外UUID一般是无序的。有些时候我们希望能使用一种简单一些的ID,并且希望ID能够按照时间有序生成。而twitter的snowflake解决了这种需求,最初Twitter把存储系统从MySQL迁移
Wesley13 Wesley13
2年前
mysql设置时区
mysql设置时区mysql\_query("SETtime\_zone'8:00'")ordie('时区设置失败,请联系管理员!');中国在东8区所以加8方法二:selectcount(user\_id)asdevice,CONVERT\_TZ(FROM\_UNIXTIME(reg\_time),'08:00','0
Wesley13 Wesley13
2年前
00:Java简单了解
浅谈Java之概述Java是SUN(StanfordUniversityNetwork),斯坦福大学网络公司)1995年推出的一门高级编程语言。Java是一种面向Internet的编程语言。随着Java技术在web方面的不断成熟,已经成为Web应用程序的首选开发语言。Java是简单易学,完全面向对象,安全可靠,与平台无关的编程语言。
Wesley13 Wesley13
2年前
MySQL部分从库上面因为大量的临时表tmp_table造成慢查询
背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_
为什么mysql不推荐使用雪花ID作为主键
作者:毛辰飞背景在mysql中设计表的时候,mysql官方推荐不要使用uuid或者不连续不重复的雪花id(long形且唯一),而是推荐连续自增的主键id,官方的推荐是auto_increment,那么为什么不建议采用uuid,使用uuid究
Python进阶者 Python进阶者
3个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这