`
qzriso
  • 浏览: 242982 次
  • 性别: Icon_minigender_1
  • 来自: ph
社区版块
存档分类
最新评论

MySQL内存使用-线程独享

阅读更多

对于任何一个数据库管理系统来说,内存的分配使用绝对可以算的上是其核心之一了,所以很多希望更为深入了解某数据库管理系统的人,都会希望一窥究竟,我也不例外。

从内存的使用方式MySQL 数据库的内存使用主要分为以下两类

    * 线程独享内存
    * 全局共享内存

今天这篇文章暂时先分析 MySQL 中主要的 “线程独享内存” 的。

在 MySQL 中,线程独享内存主要用于各客户端连接线程存储各种操作的独享数据,如线程栈信息,分组排序操作,数据读写缓冲,结果集暂存等等,而且大多数可以通过相关参数来控制内存的使用量。

 

二进制日志缓冲区(Binlog Buffer):二进制日志缓冲区主要用来缓存由于各种数据变更操做所产生的 Binary Log 信息。为了提高系统的性能,MySQL 并不是每次都是将二进制日志直接写入 Log File,而是先将信息写入 Binlog Buffer 中,当满足某些特定的条件(如 sync_binlog参数设置)之后再一次写入 Log File 中。我们可以通过 binlog_cache_size 来设置其可以使用的内存大小,同时通过 max_binlog_cache_size 限制其最大大小(当单个事务过大的时候 MySQL 会申请更多的内存)。当所需内存大于 max_binlog_cache_size 参数设置的时候,MySQL 会报错:“Multi-statement transaction required more than ‘max_binlog_cache_size’ bytes of storage”。

 

线程栈信息使用内存(thread_stack):主要用来存放每一个线程自身的标识信息,如线程id,线程运行时基本信息等等,我们可以通过 thread_stack 参数来设置为每一个线程栈分配多大的内存。

 

排序使用内存(sort_buffer_size):MySQL 用此内存区域进行排序操作(filesort),完成客户端的排序请求。当我们设置的排序区缓存大小无法满足排序实际所需内存的时候,MySQL 会将数据写入磁盘文件来完成排序。由于磁盘和内存的读写性能完全不在一个数量级,所以sort_buffer_size参数对排序操作的性能影响绝对不可 小视。排序操作的实现原理请参考:MySQL Order By 的实现分析。

 

Join操作使用内存(join_buffer_size):应用程序经常会出现一些两表(或多表)Join的操作需求,MySQL在完成某些 Join 需求的时候(all/index join),为了减少参与Join的“被驱动表”的读取次数以提高性能,需要使用到 Join Buffer 来协助完成 Join操作(具体 Join 实现算法请参考:MySQL 中的 Join 基本实现原理)。当 Join Buffer 太小,MySQL 不会将该 Buffer 存入磁盘文件,而是先将Join Buffer中的结果集与需要 Join 的表进行 Join 操作,然后清空 Join Buffer 中的数据,继续将剩余的结果集写入此 Buffer 中,如此往复。这势必会造成被驱动表需要被多次读取,成倍增加 IO 访问,降低效率。

 

顺序读取数据缓冲区使用内存(read_buffer_size):这部分内存主要用于当需要顺序读取数据的时候,如无发使用索引的情况下的全表扫 描,全索引扫描等。在这种时候,MySQL 按照数据的存储顺序依次读取数据块,每次读取的数据快首先会暂存在read_buffer_size中,当 buffer 空间被写满或者全部数据读取结束后,再将buffer中的数据返回给上层调用者,以提高效率。

 

随机读取数据缓冲区使用内存(read_rnd_buffer_size):和顺序读取相对应,当 MySQL 进行非顺序读取(随机读取)数据块的时候,会利用这个缓冲区暂存读取的数据。如根据索引信息读取表数据,根据排序后的结果集与表进行Join等等。总的来 说,就是当数据块的读取需要满足一定的顺序的情况下,MySQL 就需要产生随机读取,进而使用到 read_rnd_buffer_size 参数所设置的内存缓冲区。

 

连接信息及返回客户端前结果集暂存使用内存(net_buffer_size):这部分用来存放客户端连接线程的连接信息和返回客户端的结果集。当 MySQL 开始产生可以返回的结果集,会在通过网络返回给客户端请求线程之前,会先暂存在通过 net_buffer_size 所设置的缓冲区中,等满足一定大小的时候才开始向客户端发送,以提高网络传输效率。不过,net_buffer_size 参数所设置的仅仅只是该缓存区的初始化大小,MySQL 会根据实际需要自行申请更多的内存以满足需求,但最大不会超过 max_allowed_packet 参数大小。

 

批量插入暂存使用内存(bulk_insert_buffer_size):当我们使用如 insert … values(…),(…),(…)… 的方式进行批量插入的时候,MySQL 会先将提交的数据放如一个缓存空间中,当该缓存空间被写满或者提交完所有数据之后,MySQL 才会一次性将该缓存空间中的数据写入数据库并清空缓存。此外,当我们进行 LOAD DATA INFILE 操作来将文本文件中的数据 Load 进数据库的时候,同样会使用到此缓冲区。

 

临时表使用内存(tmp_table_size):当我们进行一些特殊操作如需要使用临时表才能完成的 Order By,Group By 等等,MySQL 可能需要使用到临时表。当我们的临时表较小(小于 tmp_table_size 参数所设置的大小)的时候,MySQL 会将临时表创建成内存临时表,只有当 tmp_table_size 所设置的大小无法装下整个临时表的时候,MySQL 才会将该表创建成 MyISAM 存储引擎的表存放在磁盘上。不过,当另一个系统参数 max_heap_table_size 的大小还小于 tmp_table_size 的时候,MySQL 将使用 max_heap_table_size 参数所设置大小作为最大的内存临时表大小,而忽略 tmp_table_size 所设置的值。而且 tmp_table_size 参数从 MySQL 5.1.2 才开始有,之前一直使用 max_heap_table_size。

 

上面所列举的 MySQL 线程独享内存仅仅只是所有线程独享内存中的部分,并不是全部,选择的原则是可能对 MySQL 的性能产生较大的影响,且可以通过系统参数进行调节。

由于以上内存都是线程独享,极端情况下的内存总体使用量将是所有连接线程的总倍数。所以各位朋友在设置过程中一定要谨慎,切不可为了提升性能就盲目的增大各参数值,避免因为内存不够而产生 Out Of Memory 异常或者是严重的 Swap 交换反而降低整体性能。

分享到:
评论

相关推荐

    MySQL内存使用之线程独享介绍

    在 MySQL 中,线程独享内存主要用于各客户端连接线程存储各种操作的独享数据,如线程栈信息,分组排序操作,数据读写缓冲,结果集暂存等等,而且大多数可以通过相关参数来控制内存的使用量。 线程栈信息使用内存...

    mysql中的内存使用.pdf

    MySQL的内存管理可以根据使用的内存类型被划分为两大类:线程独享内存和全局共享内存。 首先是线程独享内存,这一部分的内存被各个线程独立使用,不会与其他线程共享。线程独享内存的管理主要涉及以下几个参数: 1...

    MySql5.7安装到主从配置到生产环境高可用MHA部署

    MySQL 的内存使用分为线程独享内存和全局共享内存两大类: 1. **线程独享内存**:每个连接都会分配一块独享内存区域,用于保存该连接的信息,例如线程ID、线程状态等。主要涉及的参数有 thread_stack(线程堆栈大小...

    mysql数据库my.cnf配置文件

    # 联合查询操作所能使用的缓冲区大小,和sort_buffer_size一样,该参数对应的分配内存也是每连接独享 thread_cache_size = 8 # 这个值(默认8)表示可以重新利用保存在缓存中线程的数量,当断开连接时如果缓存中还有...

    mysql-20211102.pdf

    - `ibd`(InnoDB):用于独享表空间,每个InnoDB表一个单独的`.ibd`文件,存储数据和索引。 - `.ibdata`(InnoDB):共享表空间,多个表共用,可配置多个文件如`ibdata001`、`ibdata002`。 - `ibdata1`:系统表...

    processlist命令 查看mysql 线程

    - 内存使用:线程独享内存分配对系统内存使用有直接影响。 - 索引管理:通过`processlist`可以了解是否因缺少索引导致慢查询。 - 连接IP信息:查看连接MySQL的IP,有助于排查安全和性能问题。 总的来说,`...

    MySQL 4G内存服务器配置优化

    11. `sort_buffer_size = 6M`:查询排序时的缓冲区大小,每个连接独享,根据连接数和内存大小适当调整。 12. `read_buffer_size = 4M`:读查询操作的缓冲区大小,同样每个连接独享。 13. `join_buffer_size = 8M`...

    MySQL8.0内存相关参数总结

    2. **线程独享内存**: - **thread_stack**:每个线程的堆栈大小,用于存储函数调用等信息。 - **sort_buffer_size**:用于排序操作的内存,增加此值可提高排序速度,特别是处理大数据量排序时。 - **join_buffer...

    mysql-innodb

    InnoDB的数据和索引存储在表空间中,可以使用共享表空间或独享表空间。独享表空间模式下,每个表都有独立的.idb文件存储数据和索引,而.frm文件则保存元数据。表空间的移动和恢复需谨慎操作,如使用`ALTER TABLE`...

    TDSQL新考题.docx

    15. **线程独享内存**:线程独享的内存包括 read_buffer_size(读缓冲大小),因为每个线程都有自己的读缓冲。query_cache_size(查询缓存大小)是全局共享的,不是线程独享。innodb_buffer_pool_size(InnoDB 缓冲...

    实测:云RDS MySQL性能是自建的1.6倍.doc

    1. **独享规格**:提供独占的计算资源,性能稳定但成本较高。 2. **通用规格**:通过资源复用提高性价比,可能出现超卖现象,性能波动可能较大。 在测试中,注意到自建MySQL和Percona部署在阿里云ECS上,使用了...

    华为云数据库RDS性能白皮书.pdf

    - **MySQL 5.6**:提供了通用型和独享型测试数据,通过这些数据可以了解不同配置下MySQL 5.6的性能表现。 - **MySQL 5.7**:同样包括通用型和独享型测试数据,用以对比不同环境下MySQL 5.7的性能差异。 - **MySQL ...

    Linux中对MySQL优化实例详解

    `join_buffer_size`是联合查询操作的缓冲区大小,同样每连接独享,这里设为8M。 `myisam_sort_buffer_size`针对MyISAM表的排序缓冲区大小,设置为64M。 `thread_cache_size`是线程缓存大小,可以减少线程创建和...

    Java多线程并发编程和锁原理解析

    例如:Semaphore 和 ReadWriteLock 和 countdownlatch,其读锁是共享锁,写锁是独享锁。 公平锁和非公平锁 公平锁加锁前先查看是否有排队等待的线程,有的话优先处理排在前面的线程,先来先得。非公平锁线程加锁时...

    搜狐&&美团旅行面试题.docx

    - Redis使用单线程模型执行所有命令,因此对于同一客户端来说不存在并发问题。但为了保证多个客户端同时写入同一个key的安全性,Redis通过`WATCH`、`MULTI`、`EXEC`命令实现了事务功能。此外,还可以使用`lua脚本`...

    头条java面试题(10).pdf

    这个部分包括了MySQL锁的种类、行锁、表锁、悲观锁、乐观锁、共享锁、独享锁等知识点。 JVM调优 JVM调优是Java面试中一个重要的知识点,主要考察候选人的Java虚拟机性能优化能力。这个部分包括了JVM性能监控分析...

    java同步开篇入门简单介绍

    在锁的类型中,还有公平锁和非公平锁、可重入锁、独享锁/共享锁、互斥锁/读写锁等概念。比如,Java的`synchronized`默认是非公平锁,而`ReentrantLock`可以设置为公平或非公平。可重入锁允许一个线程多次获取同一锁...

    二十三种设计模式【PDF版】

    很简单一个模式,就是在内存中保留原来数据的拷贝. 设计模式之 Interpreter(解释器) 主要用来对语言的分析,应用机会不多. 设计模式之 Visitor(访问者) 访问者在进行访问时,完成一系列实质性操作,而且还可以扩展. ...

Global site tag (gtag.js) - Google Analytics