likes
comments
collection
share

MYSQL系列-各种Buffer优化二~性能增强利器

作者站长头像
站长
· 阅读数 24

排序缓冲区(Sort Buffer)

MYSQL排序整体过程

MYSQL系列-各种Buffer优化二~性能增强利器

  1. server 层从存储引擎读取符合 where 条件的记录,写入一个专门存放待排序记录的内存区域,这个内存区域叫做排序缓冲区(sort buffer)
  2. 排序缓冲区写满之后,会对缓冲区中的记录进行排序,排好序的记录组成一个数据块,数据块包含 Merge_chunk 和数据记录两部分,Merge_chunk 写入一个磁盘文件(chunk_file),数据记录写入另一个磁盘文件(temp_file)。Merge_chunk 中保存着数据记录在磁盘文件(temp_file)中的起始位置、记录数量等信息。
  3. Merge_chunk 和数据记录写入磁盘文件之后,排序缓冲区中的数据被清空,然后就可以写入其它待排序记录了,再次写满之后,缓冲区中的记录同样会进行排序,组成一个数据块,并把 Merge_chunk 和数据记录分别写入磁盘文件 chunk_file 和 temp_file。
  4. 读完符合 where 条件的所有记录之后,可能会生成多个数据块,对数据块进行 7 路归并排序,把 7 个小数据块合并成大数据块,直到合并得到的大数据块数量小于等于 15 个(如果归并排序之前,数据块数量本身就小于等于 15 个,此步骤跳过)。
  5. 最后,通过多路归并排序把小于等于 15 个数据块合并为最终的排序结果,写入磁盘文件(out_file)。

排序缓存介绍

排序缓冲区是内存缓冲区,用于存放待排序记录。对于服务器来说,内存是稀缺资源,既然排序缓冲区在内存中,其大小必然要受到限制。

相关参数说明

  1. sort_buffer_size:

    • sort_buffer_size参数用于指定排序缓冲区的大小,以字节为单位。
    • 该参数的默认值通常较小,例如256KB或512KB,但可以根据需要进行调整。
    • 增大sort_buffer_size可以提高排序操作的性能,尤其是在需要排序大量数据时。
    • 然而,设置过大的值可能会占用过多的内存资源,因此需要根据系统的可用内存和排序操作的需求进行权衡和调整。
    • 需要注意的是,连接缓冲区的大小是针对每个连接的,所以对于系统中的所有连接都会生效。
  2. max_sort_length 参数:

    • max_sort_length 是一个全局参数,用于指定排序操作中允许的最大排序键长度。
    • 默认值为 1024,表示每个排序键的最大长度为 1024 字节。
    • 该参数的目的是限制排序操作所使用的内存量,以防止过多的内存消耗。
    • 如果某个排序键的长度超过了 max_sort_length 的值,MySQL 将会使用临时文件进行排序,而不是在内存中进行。
    • 增大 max_sort_length 可以允许排序更长的键,但也会导致更多的内存使用。

连接缓冲区(Join Buffer)

MySQL Join Buffer(连接缓冲区)是MySQL中用于执行连接操作(JOIN)的一种缓冲区。它用于存储连接操作中的中间结果,以加速查询的执行。

在执行连接操作时,MySQL会将连接的两个表中的数据进行匹配,并生成结果集。这个过程可能涉及到大量的读取和比较操作,而连接缓冲区的作用就是在内存中存储部分连接操作的中间结果,以减少磁盘I/O和重复的比较操作,从而提高性能。

相关参数

  1. join_buffer_size:

    • 这是连接缓冲区的大小,以字节为单位。
    • 可以通过设置该参数来调整连接缓冲区的大小。
    • 例如,可以使用以下命令设置连接缓冲区的大小为4MB:
      SET GLOBAL join_buffer_size = 4 * 1024 * 1024;
      
    • 需要注意的是,连接缓冲区的大小是针对每个连接的,所以对于系统中的所有连接都会生效。
  2. join_buffer_space_limit:

    • 这是连接缓冲区的最大可用空间限制。
    • 默认情况下,连接缓冲区的大小可以根据需要进行动态调整,直到达到join_buffer_size设置的值。
    • 但是,可以通过设置join_buffer_space_limit参数来限制连接缓冲区的最大可用空间。
    • 例如,可以使用以下命令设置连接缓冲区的最大可用空间为2GB:
      SET GLOBAL join_buffer_space_limit = 2 * 1024 * 1024 * 1024;
      

JOIN查询方式

  • Simple Nested-Loop Join
  • Index Nested-Loop Join
  • Block Nested-Loop Join(简单-索引-缓冲区)

查询缓存(Query Cache)

查询缓存(Query Cache)是一种用于缓存查询结果的机制,可以提高重复查询的性能。然而,自MySQL 5.7.20版本起,查询缓存功能已被弃用,并在MySQL 8.0版本中完全删除。这是因为查询缓存可能带来一些性能问题,如锁竞争和内存管理等方面的开销。

查询缓存用于缓存查询结果,以避免重复执行相同的查询。

  • 优点:对于经常重复执行相同查询的应用程序,启用查询缓存可以显著提高性能。
  • 缺点:查询缓存的效果在高并发环境下可能不佳,因为对表的更新操作会导致缓存的失效,还可能引入锁竞争和额外的开销。

参数设置

  1. query_cache_type:

    • 这个参数指定查询缓存的工作方式。
    • 默认值为0,表示查询缓存被禁用。
    • 设置为1时,表示查询缓存被启用,但只缓存使用了SQL_CACHE提示的查询。
    • 设置为2时,表示查询缓存被启用,缓存所有不使用SQL_NO_CACHE提示的查询。
    • 由于查询缓存功能已被弃用,因此在MySQL 8.0及更新版本中,这个参数设置不会产生任何效果。
  2. query_cache_size:

    • 这个参数指定查询缓存的大小,用于存储查询结果。
    • 默认值为0,表示查询缓存被禁用。
    • 可以设置为一个适当的值,以控制查询缓存使用的内存大小。
    • 由于查询缓存功能已被弃用,因此在MySQL 8.0及更新版本中,这个参数设置不会产生任何效果。

日志缓冲区(Log Buffer)

日志缓冲区(Log Buffer)是MySQL中用于存储事务日志(Transaction Log)的缓冲区。它在数据库执行事务时起到关键的作用。

基本介绍

当在MySQL中对InnoDB表进行更改时,这些更改首先存储在InnoDB日志缓冲区的内存中,然后写入通常称为重做日志(redo logs)的InnoDB日志文件中。

MYSQL系列-各种Buffer优化二~性能增强利器

redo日志缓冲区是内存存储区域,用于保存要写入磁盘上的日志文件的数据。日志缓冲区大小由innodb_log_buffer_size 变量定义,默认大小为16MB。

日志缓冲区的内容定期刷新到磁盘。较大的日志缓冲区可以运行大型事务,而无需在事务提交之前将重做日志数据写入磁盘。因此,如果有更新,插入或删除许多行的事务,则增加日志缓冲区的大小可以节省磁盘I/O。

innodb_flush_log_at_trx_commit :控制如何将日志缓冲区的内容写入并刷新到磁盘。 innodb_flush_log_at_timeout :控制日志刷新频率。

如果磁盘I/O导致性能问题,则需要观察事务,例如涉及许多BLOB条目的事务。只要InnoDB日志缓冲区已满,便会将其刷新到磁盘,因此增加缓冲区大小可以减少I/O。

临时表

MySQL中的临时表是在内存或磁盘上创建的临时数据结构,用于存储在查询执行期间产生的中间结果。对于内部临时表(Internal Temporary Tables),MySQL会尝试将其存储在内存中,以提高性能。

参数介绍

  1. tmp_table_size:

    • tmp_table_size参数定义了内部临时表的最大大小。
    • 当内部临时表的大小超过了该值时,MySQL将其存储在磁盘上而不是内存中。
    • 默认值为16MB。
  2. max_heap_table_size:

    • max_heap_table_size参数定义了内存中堆表(Heap Table)的最大大小。
    • 堆表是一种特殊的内部临时表,使用内存作为存储引擎。
    • 如果一个查询需要创建堆表,并且其大小超过了该值,MySQL将尝试使用磁盘上的临时表。
    • 默认值为16MB。
  3. tmpdir:

    • tmpdir参数定义了MySQL服务器用于存储临时文件的目录。
    • 临时文件包括使用磁盘存储的临时表以及其他临时文件,如排序和临时文件。
    • 如果未指定tmpdir,MySQL将使用系统默认的临时目录。
    • 可以使用绝对路径或相对于数据目录的相对路径来设置tmpdir

参考 1.带你一步一步深入了解 MySQL Order By 文件排序 2.高性能MySQL-Join的底层实现原理 3.MySQL 数据在连接缓冲区是怎么存储的? 4.知识分享 | MySQL InnoDB 日志缓冲区(Log Buffer)讲解