MySQL 查询慢的根本原因

这里的表空间呢,指的是独立表空间,在MySQL中,表空间分为2种,分别是共享表空间和独立表空间,不过在MySQL 5.6.6及后续版本默认使用的是独立表空间,
说白了就是一个独立表空间在磁盘中会单独对应一个表空间文件,而一个表空间文件存放着MYSQL数据库中一张表的数据。 在表空间中有很多数据区组,每个数据区组中包含256个数据区,而每个数据区中又包含64个数据页,因为每个数据页的大小默认是16KB,所以也就是说一个数据区的大小是1MB。 从磁盘加载数据到MYSQL内存中,其实就是通过磁盘IO的方式,把数据页中的数据加载到缓冲池Buffer Pool中的缓存页中,然后通过InnoDB存储引擎和sql接口,一步步返回给用户。 那么,在查询的整个流程中,哪个环节最容易拖后腿呢?答案就是磁盘IO,也就是将磁盘中的数据页数据读取到Buffer Pool的缓存页这个过程。 那么,磁盘IO为什么会拖后腿呢?磁盘IO的过程大概是什么样子的呢?接下来,就很有必要来看下这一块内容了。 查询慢深层次原因揭秘:磁盘IO的过程 先来看下磁盘的物理结构,如下图:

磁盘内部的组成部分,主要为主轴、磁盘盘片、读写磁头、传动轴和传动手臂,其中数据就是存放在磁盘盘片上的,磁盘盘片被划分为了无数个小扇区,每个扇区中都有很多半径不同的环形磁道,不同的磁道中存放着不同的数据。

在实际读写数据时,主轴会让磁盘盘片转动,然后再通过传动手臂的伸展,让读写磁头在磁盘扇区的磁道上读取和写入数据,一次磁盘IO花费的时间,主要由寻道时间、旋转延迟和数据传输时间三部分构成,接下来,我们分别来看下这三部分的耗时情况。

1 寻道时间
刚才我们知道了,磁盘盘片表面上被分为了无数小扇区,每个扇区中都有很多半径不同的磁道,不同的磁道上放着不同的数据。

而寻道时间,指的是将读写磁头移动到正确半径的磁道上所需要的时间,寻道时间越短,磁盘IO操作越快,目前磁盘的平均寻道时间,一般在3~15ms,主流磁盘一般在5ms以下。

2 旋转延迟
寻道结束后,还需要读写磁头旋转到这个磁道的正确位置上才能读写数据,而旋转延迟,指的是从寻道时间结束开始,到读写磁头旋转到磁道正确位置的这段时间间隔。

但是,我们一般将磁盘旋转周期值的一半,作为旋转延迟的近似值;常见的磁盘转速有5400转和7200转,表示每分钟能转5400和7200圈。

比如,我们以7200转举例,也就是说1秒钟能转120圈,磁盘的旋转周期就是 1/120 秒,所以,旋转延迟的近似值为 1/120/2 = 4.17ms。

3 数据传输时间
传输时间,指的是将数据从磁盘盘片读出或写入的时间,一般在零点几毫秒,相对于前两个时间几乎可以忽略不计,这样来看访问一次磁盘即一次磁盘IO的时间,约等于 5ms + 4.17ms = 9ms。

磁盘的顺序读写和随机读写

另外,磁盘的数据读写,分为随机读写和顺序读写这两种,这两种读写数据的方式,与读写磁头读写数据的方式有关。

顺序读写,顾名思义就是读写磁头从磁盘中的一个位置,按照顺序依次读写磁盘盘片中的数据,速度还是挺快的,比如像MYSQL的redo log日志、binglog日志这些日志信息,比如,顺序写数据时,会相应在一个大日志文件末尾,按照顺序添加日志信息。

随机读写时,读写磁头则会在磁盘盘片中,随机切换到不同半径的磁道上读写数据,频繁切换磁道的这个过程,是非常耗时的。

所以,随机读写的速度相比于顺序读写来说,是会慢很多的,而MYSQL从磁盘中读写数据,正好是比较耗时的随机读写。

正是因为从MYSQL中查询数据,往往要发生多次耗时的随机IO,所以,我们对于一些对查询效率要求较高的数据,一般都会选择固态硬盘来存放。

固态硬盘的工作原理,简单来说就是通过电子的移动来实现数据的读写,相比于磁盘这种物理机械的运作方式,速度是快很多的,但是固态硬盘是比较贵的,基于成本考虑,一般公司大部分机器还是会选择普通机械磁盘的。

磁盘IO到底会有多慢呢?
我们回到刚才,已经知道磁盘IO的工作原理,我们也简单计算了一下,一次磁盘IO大概是9ms的样子,看上去还可以,但是9ms已经非常慢了,那到底有多慢呢,我们可以和内存的速度对比一下。

一般一次内存随机读取的速度,大概在100ns以内,而 1ms = 1000000ns,可以看到,一次磁盘IO耗时是毫秒级的,而内存是纳秒级的。

9ms = 9 * 1000000 ns / 100 ns = 90000,说白了磁盘的速度比内存慢 9万倍左右,那为什么从内存读写数据会那么快呢,简单来说,内存其实是被CPU控制的,而CPU的时钟频率的速度相比于磁盘机械运转速度,速度可以说是非常快了。

当用户发起一次查询请求,一次磁盘IO一般是搞不定的,具体发生磁盘IO的次数,还得要取决于B+树的高度和当时使用索引的情况。

极端情况下,比如没用到索引,一次查询可能会发生100多次磁盘IO,这时,磁盘IO所需的总时间大概是 9ms * 100 = 900ms,也就是0.9秒,这就差不多到秒级别了。

随着数据的快速增长,比如达到了好几亿的数据量,那需要的磁盘IO次数会大幅增加,那这个时候,一次查询所需要的时间,就会达到好几秒。

用户查询请求慢的根本原因
现在,我们知道用户查询请求慢的根本原因了吗?

其实说白了,就是随着数据表中的数据量,变得越来越大,导致磁盘IO发生的次数也相应变多了,如果我们能把磁盘IO的次数降到常数级别,那么查询速度是非常快的,所以,后边的优化都是以降低磁盘IO次数为目标。
cpu影响mysql吗
MySQL是一种开源的关系型数据库管理系统,而CPU是电脑的“大脑”,两者密切相关。在MySQL中,对于查询和处理大量数据,CPU使用率会显著增加。CPU的性能和配置对MySQL的性能有很大的影响,下面详细说说。

CPU的性能和核数决定了服务器的处理能力。与MySQL类似的应用程序需要大量的CPU资源,以便快速处理请求。因此,如果CPU存在瓶颈,那么数据库作为一种I/O密集型应用,将不能得到充分的利用,从而影响MySQL的性能。

与单核CPU相比,具有更多核心的CPU可以提高MySQL的性能。这是因为在多核CPU上,多个线程可以并行执行,从而加快查询和数据处理的速度。另外,更高的CPU频率也可以提高性能。

除了CPU的数量和频率之外,缓存大小对于MySQL性能也很重要。CPU缓存是一个用于存储近期使用的指令和数据的高速内存系统。尽管CPU缓存的大小通常没有直接限制MySQL性能的大小,一个合理的缓存值可以提高CPU缓存的命中率,从而缩短了查询的响应时间。

// 下面是一个在MySQL中执行的简单查询语句
SELECT username, email FROM users WHERE age >30;
总之,CPU配置和性能对MySQL性能有很大的影响。为了提高MySQL的性能,可以考虑增加CPU的核数和频率,同时增加适当的缓存大小,以便加速查询处理。

 

posted @ 2024-11-19 17:00  【君莫笑】  阅读(31)  评论(0编辑  收藏  举报