Innodb数据空间占用探索

news2025/2/27 1:21:59

了解数据存储空间占用,可以更方便我们再企业中对于数据库相关优化做评估。

一、查看当前数据表空间占用信息

首先这里准备一张数据库表约2.3w数据量:

CREATE TABLE `project` (
  `tenantsid` bigint(20) NOT NULL DEFAULT '0' COMMENT '租户ID',
  `project_id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '主键',
  `code` bigint(20) NOT NULL DEFAULT '0' COMMENT '项目编号',
  `name` varchar(72) COLLATE utf8_bin DEFAULT '' COMMENT '项目名称',
  PRIMARY KEY (`project_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=59840 DEFAULT CHARSET=utf8 COLLATE=utf8_bin COMMENT='项目档'  

查看表存储空间大小方式有很多

1、通过iinformation_schema.tables查看数据空间占用信息

select table_name,data_length,index_length from information_schema.tables where table_name = 'project';

 按照官网介绍:

DATA_LENGTH

对于MyISAMDATA_LENGTH 是数据文件的长度,以字节为单位。

对于InnoDBDATA_LENGTH 是为聚集索引分配的大约空间量(以字节为单位)。具体来说,它是聚集索引大小(以页为单位)乘以InnoDB页大小。

INDEX_LENGTH

对于MyISAMINDEX_LENGTH 是索引文件的长度,以字节为单位。

对于InnoDBINDEX_LENGTH 是为非聚集索引分配的大约空间量(以字节为单位)。具体来说,它是非聚集索引大小的总和(以页为单位)乘以 InnoDB页大小。

DATA_LENGTH  = 聚集索引大小(以页为单位)乘以InnoDB页大小

INDEX_LENGTH  = 非聚集索引大小(以页为单位)乘以InnoDB页大小

2、查看page页大小配置

show status like '%page_size%';

可以看到默认的页大小为16kb

3、查看当前project表聚簇索引使用了多少page

innodb_space -s ibdata1 -T firestation/project space-indexes

可以看到这里面PRIMARY一共分配了97个page页占用空间 = 97*16*1024 = 1,589,248可以看到正好是DATA_LENGTH大小

前面也说到了当97个表只是当前project真实数据占用的空间大小,对于表来说,还存在其他的的空间占用,比如缓存、元数据等等,所以DATA_LENTGTH表示的只是真实数据的大小。当然对于日常的空间占用评估是足够了。

那我们深入探索下,project真实存储空间占用情况。

4、查看project表使用总page数

innodb_space -s ibdata1 -T firestation/project space-page-type-summary

 可以看到project实际存储时使用到了704个page页,所以理论上应该占用空间704*16*1024=11,534,336

其实mysql在information_schema中提供了innodb系列的元数据表,它记录了innodb底层存储时真实的元数据信息,例如information_schema.innnodb_sys_tablespace(我这里是mysql5.7不同版本的名称不同,看官网说明)中就可以查看表真实存储空间大小。

5、查看project真实占用空间大小

select * from information_schema.innodb_sys_tablespaces where name = 'firestation/project';

  • FILE_SIZE

    文件的表观大小,表示未压缩的文件的最大大小。

  • ALLOCATED_SIZE

    文件的实际大小,即磁盘上分配的空间量。

可以看到这里的File_size就是上面通过真实数据page数计算出来的结果。

所以结论:

1、可以通过information_schema.table查看DATA_LENGTH,这个为当前主键索引也就是真实数据的空间占用大小。

2、可以通过information_schema.innodb_sys_tablespace 查看File_size,这个为当前project总占用空间大小

二、每行数据占用空间

其实通过上述的结论,就可以大致的评估出每行数据空间占用大小,总大小/行数,这里我们更深入了解下一行数据怎么计算的空间占用大小。

1、查看每一行数据占用空间大小

(1)首先先确定project存储tree一共为几层 , 这里先介绍一种查看到方式,后续在介绍另一种。

通过innodb_space工具查看:

这里可以看到PRIMARY索引一共分2层,第1层非叶子节点只有一个page,第2层叶子节点共95个page页,需要注意的是这里叶子节点为0层,依次往上推。

(2)查看每一层tree空间占用

1层,非叶子节点(此处为root节点):

innodb_space -s ibdata1 -T firestation/project -I PRIMARY -l 1 index-level-summary

page: page页编号,这里为3,也就是上面看到的root节点page编号

index:索引编号

level:当前page所处的层级

data:当前page占用空间大小

free:当前page空闲空间大小,因为page大小固定16kg,所以就会存在页用不满的现象

recoreds:当前page存储的数据行数,这里因为是非叶子节点,所以指的是主键行数。

min_key:当前页中最小的索引列,这里是主键。

0层,非叶子节点(此处为root节点):

从这里就可以看出来,大约每行数据占用15000/250 = 60字节空间

行空间占用和字段数据有密切的关系,如果字段占用空间小(比如字段栏位少,无长文本字段等)那page可以存储更多的行数,整体的占用空间小,B+树层级少,查询速度快。

这里以page#5为例,看下当前page页空间分布说明:

innodb_space -s ibdata1 -T firestation/project -p 5 page-illustrate

这张图就是展示了PAGE一个详细的空间结构,前面文章也介绍过,这里不再赘述。

可以看到Record Header + Record Data 是真实数据产生的空间占用 = 1631+13471 =15102也是验证了上面看到的page空间占用。

三、每行数据空间评估

根据上面的数据结果,选择一个project_id = 33819的一行数据,从空间上来看为15102字节/233 =64字节

当前行数据:

我们知道bigint占用8字节,varchar是不定长,一个汉字3字节。按照这样的算法

空间:8+8+8+12 = 36字节,远小于60字节,这是为什么呢?

这个就是需要了解行格式知识相关了:【Mysql】 InnoDB引擎深入- 行格式_mysql 5.6 innodb引擎 不支持行格式为:dynamic_Survivor001的博客-CSDN博客

首先确定我们目前的行格式是什么,这个很好确定:

根据行格式的知识,我们知道一行数据除了真实的数据之外还会记录一些额外的信息。

  • 在这里以project_id =33819数据大致计算下
  • 存在变长字段,且长度<255,则需要1个字节记录其长度(这里共1~2字节,记录最大值65535,所以这就是为什么一行数据不能超过这个阈值)
  • 记录头5个字节
  • 除此之外,数据里面处理记录真实数据外还记录其他内比如row_id(6字节),回滚指针(7字节)、事务id(6字节)
  • 总计:1+5+7+6+6= 25(字节)
  • 所以:真实数据36 + 25 ~= 60字节, 这样一看就差不多了。
  • 总结:
  • 一行数据一般来说差不多占用空间 = 25字节 + 字段栏位真实占用空间,当然如果一行数据存在大数据内容,可能一行数据就超过了page大小,就可能跨页,这个时候就会行溢出。需要更多的页来记录其内容,次数就会占用更多的空间,因为page本身也会有额外的空间占用。所以这就是为什么大数据栏位建议独立出来不要和普通字段放在一起,而text、blog有独立BLOB PAGE原因。
  • 行溢出:【Mysql】 InnoDB引擎深入- 行溢出_innodb行溢出-CSDN博客

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1278562.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Redis RDB

基于内存的 Redis, 数据都是存储在内存中的。 那么如果重启的话, 数据就会丢失。 为了解决这个问题, Redis 提供了 2 种数据持久化的方案: RDB 和 AOF。 RDB 是 Redis 默认的持久化方案。当满足一定条件的时候, 会把当前内存中的数据写入磁盘, 生成一个快照文件 dump.rdb。Redi…

thinkphp 5.1 对数据库查出来的字段进行预处理

比如数据库的设计是下面这样子&#xff1a; 我想展示的是这个样子&#xff1a; 前端可以处理。 Think PHP的处理方式&#xff1a; 定义属性 &#xff1a; $this->customize 任意值;//这里的之没有作用 <?phpnamespace app\hs\controller\shop;use app\daogou\mo…

C++ list容器

文章目录 C++ list容器list基本概念list构造函数list 赋值和交换list 大小操作list 插入和删除list 数据存取list 反转和排序排序案例C++ list容器 list基本概念 功能:将数据进行链式存储 链表(list)是一种物理存储单元上非连续的存储结构,数据元素的逻辑顺序是通过链表中…

ipvlan介绍

最近使用docker&#xff0c;涉及到需要跨多台物理机部署系统&#xff0c;查了好多资料&#xff0c;最后查到了ipvlan。那什么是vlan&#xff0c;什么又是ipvlan。 交换机层面的vlan&#xff0c;是按802.1Q规范&#xff0c;在链路层中加了4字节的标识vlan的数据&#xff0c;交换…

12.1 二叉树简单题

101. 对称二叉树 给你一个二叉树的根节点 root &#xff0c; 检查它是否轴对称。 示例 1&#xff1a; 输入&#xff1a;root [1,2,2,3,4,4,3] 输出&#xff1a;true 思路&#xff1a;对称二叉树 有一个特点是以 中左右顺序遍历左子树的结果会等于 中右左顺序遍历右子树的结果…

Linux的基本指令(4)

目录 20.tar指令&#xff08;重要&#xff09;&#xff1a;打包/解包&#xff0c;不打开它&#xff0c;直接看内容 21.bc指令 22.uname –r指令&#xff1a; 23.重要的几个热键[Tab],[ctrl]-c, [ctrl]-d 20.tar指令&#xff08;重要&#xff09;&#xff1a;打包/解包&#…

Hdoop学习笔记(HDP)-Part.08 部署Ambari集群

目录 Part.01 关于HDP Part.02 核心组件原理 Part.03 资源规划 Part.04 基础环境配置 Part.05 Yum源配置 Part.06 安装OracleJDK Part.07 安装MySQL Part.08 部署Ambari集群 Part.09 安装OpenLDAP Part.10 创建集群 Part.11 安装Kerberos Part.12 安装HDFS Part.13 安装Ranger …

深度学习(四):pytorch搭建GAN(对抗网络)

1.GAN 生成对抗网络&#xff08;GAN&#xff09;是一种深度学习模型&#xff0c;由两个网络组成&#xff1a;生成器&#xff08;Generator&#xff09;和判别器&#xff08;Discriminator&#xff09;。生成器负责生成假数据&#xff0c;而判别器则负责判断数据是真实的还是 f…

cnpm 安装后无法使用怎么办?

问题的原因 cnpm 安装成功&#xff0c;但是却无法使用&#xff0c;一般分为两种情况&#xff0c;一种是提示无法执行命令&#xff0c;另一种是可以执行但是执行时报错&#xff0c;下面分别说明遇到这两种情况的解决方案。 解决方案 问题一&#xff1a;无法执行相关命令 首先…

Docker快速入门(docker加速,镜像,容器,数据卷常见命令操作整理)

Docker本质是将代码所需的环境依赖进行打包运行,而在Docker中最重要的是镜像和容器 镜像:可以简单地理解为每启动一个docker镜像就会占用计算机一个进程,这个进程和另外起的docker镜像的进程是相互独立的,以数据库为例,每个镜像都会copy一份数据库,在他所在的进程中.别的镜像在…

根文件系统构建-对busybox进行配置

一. 简介 本文来学习 根文件系统的制作中&#xff0c;关于 busybox的配置。 本文继上一篇 busybox中文支持的设置&#xff0c;地址如下&#xff1a; 根文件系统构建-busybox中文支持-CSDN博客 二. 根文件系统构建-busybox配置 1. 配置 busybox 与我们编译 Uboot 、 Lin…

DBeaver 社区版(免费版)下载、安装、解决驱动更新出错问题

DBeaver 社区版&#xff08;免费版&#xff09; DBeaver有简洁版&#xff0c;企业版&#xff0c;旗舰版&#xff0c;社区版&#xff08;免费版&#xff09;。除了社区版&#xff0c;其他几个版本都是需要付费的&#xff0c;当然相对来说&#xff0c;功能也要更完善些&#xff…

HashMap源码全面解析

注&#xff1a;本篇文章是在JDK1.8版本源码进行分析。 一、概述 HashMap 是基于哈希表的 Map接口的实现&#xff0c;是以 key-value 存储形式存在&#xff0c;即主要用来存储键值对。 HashMap的类图&#xff1a; HashMap继承抽象类AbstractMap&#xff0c;实现了Map、Clonea…

select选择框里填充图片,下拉选项带图片

遇到一个需求&#xff0c;选择下拉框选取图标&#xff0c;填充到框里 1、效果展示 2、代码 <el-form-item label"工种图标" class"Form_icon Form_label"><el-select ref"select" :value"formLabelAlign.icon" placeholder&…

2023年第十二届数学建模国际赛小美赛B题工业表面缺陷检测求解分析

2023年第十二届数学建模国际赛小美赛 B题 工业表面缺陷检测 原题再现&#xff1a; 金属或塑料制品的表面缺陷不仅影响产品的外观&#xff0c;还可能对产品的性能或耐久性造成严重损害。自动表面异常检测已经成为一个有趣而有前景的研究领域&#xff0c;对视觉检测的应用领域有…

PyQt6 QRadioButton单选按钮控件

​锋哥原创的PyQt6视频教程&#xff1a; 2024版 PyQt6 Python桌面开发 视频教程(无废话版) 玩命更新中~_哔哩哔哩_bilibili2024版 PyQt6 Python桌面开发 视频教程(无废话版) 玩命更新中~共计33条视频&#xff0c;包括&#xff1a;2024版 PyQt6 Python桌面开发 视频教程(无废话…

Opencv框选黑色字体进行替换(涉及知识点:selectROI,在控制台输入字体大小,颜色,内容替换所选择的区域)

import cv2 from PIL import Image,ImageDraw,ImageFont import numpy as npimg_path ../img/ img_clean_path ../img_clean/ name xiao_ben suf .pngimg cv2.imread(img_pathnamesuf) cv2.imshow(original, img)# 选择ROI roi cv2.selectROI(windowName"original&q…

Linux多核飞控

Linux多核飞控是一种基于多核处理器构建的飞控系统&#xff0c;用于控制飞行器的飞行。这种飞控系统使用Linux操作系统作为主要的控制平台&#xff0c;可以支持多个处理器核心同时工作&#xff0c;以实现更高的性能和更快的响应速度。 Linux通常用于具有较高计算量和较大内存需…

Python读取json数据导出到Excel

一、JSON字符串转换为Python对象 导入Python的json模块。该模块包含两个重要的功能-loads和load,读取JSON文件&#xff0c;并将JSON数据解析为Python数据&#xff0c;除了JSON&#xff0c;我们还需要Python的原生函数open()。一般loads用于读取JSON字符串&#xff0c;而load()用…

【数据中台】开源项目(4)-BitSail

介绍 BitSail是字节跳动开源的基于分布式架构的高性能数据集成引擎, 支持多种异构数据源间的数据同步&#xff0c;并提供离线、实时、全量、增量场景下的全域数据集成解决方案&#xff0c;目前服务于字节内部几乎所有业务线&#xff0c;包括抖音、今日头条等&#xff0c;每天同…