1 逻辑存储结构
1.1 表空间
- 共享表空间ibdata1 存放undo信息、系统事物信息、二次写缓冲
- innodb_file_per_table ON打开后每一个table都有一个表空间,存放数据、索引、插入缓冲
1.2 段
数据段、索引段、回滚段
1.3 区
- 每个区1M,由64个连续的页组成,每个页16K
- 引擎最多每次可以申请4个区,保证数据的顺序性能
1.4 页
- B+树索引本身并不能找到具体的一条记录,只能找到该记录所在的页,之后引擎把页加载到内存,通过PageDirectory再进行二叉查找
1.5 行
官网 https://dev.mysql.com/doc/refman/5.7/en/innodb-row-format.html#innodb-row-format-defining
行记录格式 innodb_default_row_format 默认 DYNAMIC
- REDUNDANT
- COMPACT
768前缀字节+20字节指针 -> off page - DYNAMIC
20字节指针 -> off page -
COMPRESSED
对off page内容进行zlib算法压缩(BLOB TEXT VARCHAR)
COMPACT
变长字段长度列表 | NULL | 记录头信息 | 隐藏列 | 字段1 | 字段2 | 字段n |
---|
- 变长字段长度列表
按列的顺序逆序排列,最多两个字节(所以varchar长度< 2^16-1=65535)
<todo>待验证?
一个字节可以最多表示255,但是 MySQL 设计长度表示时,为了区分是否是一个字节表示长度,规定,如果最高位为1,那么就是两个字节表示长度,否则就是一个字节。例如,01111111,这个就代表长度为 127,而如果长度是 128,就需要两个字节,就是 10000000 10000000,首个字节的最高位为1,那么这就是两个字节表示长度的开头,第二个字节可以用所有位表示长度,并且需要注意的是,MySQL采取 Little Endian 的计数方式,低位在前,高位在后,所以 129 就是 10000001 10000000。同时,这种标识方式,最大长度就是 2^15 - 1 = 32767,也就是32 KB
- NULL标志位
逆序排列,二进制位标志(1是null,0不是null) - 记录头信息record header 5B
next-recorder 下一行相对位置(所以在页中行就像一个链表) - 隐藏列
rowid 6B
事物id 6B
回滚指针 7B
参考资料
https://blog.csdn.net/KouLouYiMaSi/article/details/101475473
https://blog.csdn.net/zhxdick/article/details/107049949
https://blog.csdn.net/qq_35590091/article/details/107361172