一、优化目标
1、减少 IO 次数
IO永久是数据库最随意马虎瓶颈的地方,这是由数据库的职责所决定的,大部分数据库操作中超过90%的韶光都是 IO 操作所占用的,减少 IO 次数是 SQL 优化中须要第一优先考虑,当然,也是奏效最明显的优化手段。

2、降落 CPU 打算
除了 IO 瓶颈之外,SQL优化中须要考虑的便是 CPU 运算量的优化了。order by,group by,distinct … 都是花费 CPU 的大户(这些操作基本上都是 CPU 处理内存中的数据比较运算)。当我们的 IO 优化做到一定阶段之后,降落 CPU打算也就成为了我们 SQL 优化的主要目标。
MySql查询过程
二 优化方法
1.SQL语句优化
明确了优化目标之后,我们须要确定达到我们目标的方法。对付SQL语句来说,达到上述2个优化目标的方法实在只有一个,那便是改变SQL的实行操持,让他只管即便“少走弯路”,只管即便通过各种“捷径”来找到我们须要的数据,以达到“减少IO次数”和“降落CPU打算”的目标。
1)只管即便少 join
MySQL 的上风在于大略,但这在某些方面实在也是其劣势。MySQL优化器效率高,但是由于其统计信息的量有限,优化器事情过程涌现偏差的可能性也就更多。对付繁芜的多表 Join,一方面由于其优化器受限,再者在Join这方面所下的功夫还不足,以是性能表现离Oracle等关系型数据库前辈还是有一定间隔。但如果是大略的单表查询,这一差距就会极小乃至在有些场景下要优于这些数据库前辈。
2)只管即便少排序
3)排序操作会花费较多的 CPU 资源,以是减少排序可以在缓存命中率高档 IO 能力足够的场景下会较大影响 SQL的相应韶光。
4)只管即便避免 select ,并只管即便用join代替子查询
5)只管即便少利用“or”关键字
当 where 子句中存在多个条件以“或”并存的时候,MySQL 的优化器并没有很好的办理其实行操持优化问题,再加上 MySQL 特有的 SQL 与 Storage 分层架构办法,造成了其性能比较低下,很多时候利用 union all 或者是union(必要的时候)的办法来代替“or”会得到更好的效果。
6)只管即便用 union all 代替 union
union 和 union all 的差异紧张是前者须要将两个(或者多个)结果凑集并后再进行唯一性过滤操作,这就会涉及到排序,增加大量的 CPU 运算,加大资源花费及延迟。以是当我们可以确认不可能涌现重复结果集或者不在乎重复结果集的时候,只管即便利用 union all 而不是 union。
7)避免类型转换
8)能用DISTINCT的就不用GROUP BY
9)只管即便不要用SELECT INTO语句
10)从全局出发优化,而不是片面调度
SQL 优化不能是单独针对某一个进行,而应充分考虑系统中所有的 SQL,尤其是在通过调度索引优化 SQL的实行操持的时候,千万不能顾此失落彼,因小失落大。
2.表构造优化
由于MySQL数据库是基于行(Row)存储的数据库,而数据库操作 IO 的时候因此 page(block)的办法,也便是说,如果我们每条记录所占用的空间量减小,就会使每个page中可存放的数据行数增大,那么每次 IO 可访问的行数也就增多了。反过来说,处理相同行数的数据,须要访问的 page 就会减少,也便是 IO 操作次数降落,直接提升性能。
数据类型选择
原则是:数据行的长度不要超过8020字节,如果超过这个长度的话在物理页中这条数据会占用两行从而造成存储碎片,降落查询效率;字段的长度在最大限度的知足可能的须要的条件下,该当尽可能的设得短一些,这样可以提高查询的效率,而且在建立索引的时候也可以减少资源的花费。
1)数字类型:非万不得已不要利用DOUBLE,不仅仅只是存储长度的问题,同时还会存在精确性的问题。同样,固定精度的小数,也不建议利用DECIMAL,建议乘以固定倍数转换成整数存储,可以大大节省存储空间,且不会带来任何附加掩护本钱。
2)字符类型:定长字段,建议利用 CHAR 类型(char查询快,但是耗存储空间,可用于用户名、密码等长度变革不大的字段),不定长字段只管即便利用 VARCHAR(varchar查询相对慢一些但是节省存储空间,可用于评论等长度变革大的字段),且仅仅设定适当的最大长度,而不是非常随意的给一个很大的最大长度限定,由于不同的长度范围,MySQL也会有不一样的存储处理。
3)韶光类型:只管即便利用TIMESTAMP类型,由于其存储空间只须要DATETIME 类型的一半。对付只须要精确到某一天的数据类型,建议利用DATE类型,由于他的存储空间只须要3个字节,比TIMESTAMP还少。不建议通过INT类型类存储一个unix timestamp 的值,由于这太不直不雅观,会给掩护带来不必要的麻烦,同时还不会带来任何好处。
4)ENUM &SET:对付状态字段,可以考试测验利用 ENUM 来存放,由于可以极大的降落存储空间,而且纵然须要增加新的类型,只要增加于末端,修正构造也不须要重修表数据。
字符编码
字符集直接决定了数据在MySQL中的存储编码办法,由于同样的内容利用不同字符集表示所占用的空间大小会有较大的差异,以是通过利用得当的字符集,可以帮助我们尽可能减少数据量,进而减少IO操作次数。
只管即便利用 NOT NULL
NULL 类型比较分外,SQL 难优化。虽然 MySQL NULL类型和 Oracle 的NULL有差异,会进入索引中,但如果是一个组合索引,那么这个NULL 类型的字段会极大影响全体索引的效率。虽然 NULL空间上可能确实有一定节省,倒是带来了很多其他的优化问题,不但没有将IO量省下来,反而加大了SQL的IO量。以是只管即便确保 DEFAULT 值不是 NULL,也是一个很好的表构造设计优化习气。
3.架构优化
分布式和集群化
1)负载均衡。负载均衡集群是由一组相互独立的打算机系统构成,通过常规网络或专用网络进行连接,由路由器衔接在一起,各节点相互协作、共同负载、均衡压力,对客户端来说,全体群集可以视为一台具有超高性能的独立做事器。MySQL一样平常支配的是高可用性负载均衡集群,具备读写分离,一样平常只对读进行负载均衡。
2)读写分离。读写分离大略的说是把对数据库读和写的操作分开对应不同的数据库做事器,这样能有效地减轻数据库压力,也能减轻io压力。主数据库供应写操作,从数据库供应读操作,其实在很多系统中,紧张是读的操作。当主数据库进行写操作时,数据要同步到从的数据库,这样才能有效担保数据库完全性。
3)数据切分。通过某种特定的条件,将存放在同一个数据库中的数据分散存放到多个数据库上,实现分布存储,通过路由规则路由访问特定的数据库,这样一来每次访问面对的就不是单台做事器了,而是N台做事器,这样就可以降落单台机器的负载压力。
4.其他优化
1)适当利用视图加速查询。把表的一个子集进行排序并创建视图,有时能加速查询(特殊是要被多次实行的查询)。它有助于避免多重排序操作,而且在其他方面还能简化优化器的事情。视图中的行要比主表中的行少,而且物理顺序便是所哀求的顺序,减少了磁盘I/O,以是查询事情量可以得到大幅减少。
2)算法优化。只管即便避免利用游标,由于游标的效率较差,如果游标操作的数据超过1万行,那么就该当考虑改写。利用基于游标的方法或临时表方法之前,应先探求基于集的办理方案来办理问题,基于集的方法常日更有效。与临时表一样,游标并不是不可利用。对小型数据集利用 FAST_FORWARD 游标常日要优于其他逐行处理方法,尤其是在必须引用几个表才能得到所需的数据时。
3)封装存储过程。经编译和优化后存储在数据库做事器中,运行效率高,可以降落客户机和做事器之间的通信量,有利于集中掌握,易于掩护。
下面约请大家进入【Python自动化测试学习互换群】进群办法如下:
关注我的头条号,私信:测试,即可约请你进群学习互换~~