开发者

MySQL之InnoDB引擎中的Compact行格式用法

目录
  • 1、背景
  • 2、数据示例
  • 3、Compact解释
    • 【1】组成
    • 【2】头部信息
    • 【3】隐藏列
    • 【4】数据列
  • 4、总结

    1、背景

    mysql中数据存储是存储引擎干的事,InnoDB存储引擎以页为单位存储数据,每个页的大小为16KB,平时我们操作数据库都是以行为单位进行增删改查,行数据是存储在页上的,行的格式有4种:Compat、Redundant、Dynamic、Compressed,今天我们来讲一下Compat行格式。

    2、数据示例

    我们建表语句中使用的varchar、text、blob等类型不确定长度的就使用了Compact行格式,为了方便理解我们手动创建一个表并且插入两条记录,后面都结合这两条记录来进行Compat行格式讲解,表和记录如下:

    • 创建表
    CREATE TABLE test_compact
    (
        id INT AUTO_INCREMENT PRIMARY KEY,
        str1 VARCHAR(255) NOT NULL DEFAULT '',
        str2 VARCHAR(255),
        str3 CHAR(5)
    ) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 ROW_FORMAT=COMPACT;
    
    • 插入数据
    INSjavascriptERT INTO test_compact (str1, str2, str3)
    VALUES ('AA', 'BB', 'CCC'),
           ('AAA', NULL, NULL);
    
    • 查看数据
    mysql [xxx]> select * from test_compact;
    +----+------+------+------+
    | id | str1 | str2 | str3 |
    +----+------+------+------+
    |  1 | AA   | BB   | CCC  |
    |  2 | AAA  | NULL | NULL |
    +----+------+------+------+
    2 rows in set (0.001 sec)
    
    • 查看表的行格式
    mysql [xxx]> show table  status like 'test_compact' \G;
    *************************** 1. row ***************************
                Name: test_compact
              Engine: InnoDB
             Version: 10
          Row_format: Compact //目前表使用的行格式
                Rows: 2
      Avg_row_length: 8192
         Data_length: 16384
     Max_data_length: 0
        Index_length: 0
           Data_free: 0
      Auto_increment: 3
         Create_time: 2024-12-13 17:20:47
         Update_time: 2024-12-13 17:21:02
          Check_time: NULL
           Collation: utf8mb4_general_ci
            Checksum: NULL
      Create_options: row_format=COMPACT  //创建表时指定的格式
             Comment: 
    Max_index_length: 0
           Temporary: N
    1 row in set (0.001 sec)
    

    3、Compact解释

    【1】组成

    Compact行格式组成图如下:

    MySQL之InnoDB引擎中的Compact行格式用法

    Compact行由头部信息+隐藏行+数据列三部分组成。

    • 头部信息:由三部分组成,可变长度列的实际长度信息、列是否为NULL信息、描述记录信息。
    • 隐藏列:有三列,DB_ROW_ID、DB_TRX_ID、DB_ROLL_PTR,后面详细讲解。
    • 数据列:每一列的值。

    【2】头部信息

    头部信息可以如图表示:

    MySQL之InnoDB引擎中的Compact行格式用法

    接下来就结合上面创建的test_compact表和插入的记录进行理解。

    可变长度列指的就是表中的str1和str2字段,因为str1js和str2长度不固定,所以需要额外花费空间来记录str1和str2的长度,str1和str2的值只有不为NULL的时候才需要记录长度,并且str1和str2长度的顺序是根据列顺序的逆序来存放。

    存放str1和str2长度大小为1个或者2个字节,判断方法是:可变字段存储的最大字节>255字节并且真实存储的字节数>127字节就使用2个字节存储长度,否则使用1个字节存储长度。

    可变字段存储的最大字节=varchar(n)里的n * 字符集的最大字节数。n代表的是字符数,而我们用的utf8mb4字符集1个字符用1~4个字节表示,可以用如下命令看:

    mysql [xxx]> show charset like 'utf8mb4';
    +---------+---------------+--------------------+--------+
    | Charset | Description   | Default collation  | Maxlen |
    +---------+---------------+--------------------+--------+
    |http://www.devze.com utf8mb4 | UTF-8 Unicode | utf8mb4_general_ci |      4 |
    +---------+---------------+--------------------+--------+
    1 row in set (0.001 sec)
    

    可以看到utf8mb4可以表示的一个字符最大字节为4,所以str1和str2列可以存储的最大字节数为255 * 4 = 4080,ASCII字符只占用1个字节,第一条记录中的str1和str2实际长度都为2个字节。

    同样的str3的类型为CHAR(5),根据字符集决定存它储字节的范围为5~20,所以str3的长度信息也需要进行存储。

    第一条记录str3内容’CCC’长度看起来虽然js为3,实际上长度为5,这是为了防止更新str3为大于3小于5的数据时,以前的空间就成为了空间碎片需要释放。

    可以用下图表示上面2条记录长度的存储信息:

    MySQL之InnoDB引擎中的Compact行格式用法

    可以为NULL列表指的就是没有NOT NULL修饰的str2和str3列,用二进制的0和1来表示列是否为NULL值,0代表非NULL,1代表NULL,根据列的顺序逆序排列NULL信息,必须用二进制的整数倍来存储NULL信息,不足1字节高位补0,上面2条记录的NULL信息如下:

    MySQL之InnoDB引擎中的Compact行格式用法

    行记录描述信息是由5个字节也就是40个二进制位组成,不同位代表不同的含义,不做过多解释。

    【3】隐藏列

    InnoDB存储引擎会为每一行数据额外分配三个列:DB_ROW_ID、DB_TRX_ID、DB_ROLphpL_PTR,通过表格来理解一下:

    隐藏列描述大小
    DB_ROW_ID唯一标识6字节
    DB_TRX_ID事务id6字节
    DB_ROLL_PTR指向要回滚数据的地址7字节

    DB_ROW_ID只有主键和unique健都不存在时,InnoDB存储引擎会创建一个大小为6字节作为隐藏主键id使用。

    【4】数据列

    数据列只需要注意值为NULL的列不需要再去花空间去存储,因为头部信息的NULL列表已经存储了是否为NULL,所以上面2条记录完整表示如下:

    MySQL之InnoDB引擎中的Compact行格式用法

    4、总结

    本篇文章讲了Compact行格式组成,其它几种格式都差不多,Redundant会记录所有列的长度信息,通过相邻列的偏移量来计算列的长度;Dynamic、Compressed格式在行溢出(列数据过于大页面存不下)时列数据只存储其它页的地址,数据全存储在其它页通过链表连接;Compact和Redundant会在当前页存储一部分数据信息和在其它页的剩余数据地址。

    以上为个人经验,希望能给大家一个参考,也希望大家多多支持编程客栈(www.devze.com)。

    0

    上一篇:

    下一篇:

    精彩评论

    暂无评论...
    验证码 换一张
    取 消

    最新数据库

    数据库排行榜