GaussDB查询表空间大小语句及原理
GaussDB查询表空间大小
-- 查询版本
select version(); -- GuassDB_T_1.2.1.SPC135.B002Release b7197fd195
-- 单个Segment的物理占用字节数
select * from MY_SEGMENTS;
-- 一张表的总字节大小=该表所有Segment的BYTES之和
select
segment_name as 表名,
sum(bytes) as 总字节数, -- 汇总所有DN上的Segment大小
sum(bytes)/1024/1024 as 总大小_MB -- 转换为MB更易读
from MY_SEGMENTS
where
segment_type = 'TABLE' -- 只保留表类型的Segment
-- and segment_name = 'USER_INFO' -- 指定表名(大写,GuassDB默认区分大小写)
-- and owner = 'USER1' -- 可选:过滤表所有者,避免歧义
group by segment_name;
一、基础前提:GuassDB 的 MPP 架构与数据分段(Segment)
GuassDB 是典型的MPP(大规模并行处理)数据库,其核心设计是将数据 “分片存储、并行计算”—— 这是理解MY_SEGMENTS作用的关键:
- 数据节点(DN):GuassDB 集群包含多个 DN(Data Node),每个 DN 是独立的存储和计算单元;
- 数据分段(Segment):当创建一张表时,GuassDB 会根据预设的 “分片策略”(如哈希分片、范围分片),将表的完整数据拆分成多个逻辑分片,每个分片对应一个「Segment」,并分配到不同的 DN 上存储;
- Segment 的物理载体:每个 Segment 本质是 DN 上的一组物理数据文件(包含数据块、索引块、管理块等),表的实际数据就分散存储在这些 Segment 的物理文件中。
简单说:一张表的完整数据 = 多个 DN 上的 Segment 数据之和,表的 “字节大小” 本质是所有 Segment 物理占用空间的总和。
二、核心角色:MY_SEGMENTS 是 “Segment 元数据的系统字典表”
MY_SEGMENTS 是 GuassDB 内置的系统表(数据字典表),专门用于存储集群中所有「Segment」的元数据信息 —— 包括 Segment 对应的对象(表、索引等)、存储位置、物理大小等关键属性。
可以把它理解为 GuassDB 的 “Segment 资产台账”:每一个 Segment 在创建、修改、删除时,系统都会自动更新这张表的记录,确保元数据与实际存储状态一致。
三、关键机制:MY_SEGMENTS 如何记录 “字节大小”?
MY_SEGMENTS 能查询到表的字节大小,核心是它通过实时维护 Segment 的物理存储元数据实现的,具体分为 3 个步骤:
1. Segment 创建时:初始化元数据
当用户执行 CREATE TABLE 创建表时:
- GuassDB 根据分片策略在多个 DN 上创建对应数量的 Segment(如 3 个 DN 则可能创建 3 个 Segment);
- 系统自动在 MY_SEGMENTS 中插入一条 / 多条记录(每个 Segment 对应一条),并初始化关键字段:
SEGMENT_NAME:对应表名(或索引名,区分 Segment 类型);SEGMENT_TYPE:标记 Segment 类型(TABLE表示表段、INDEX表示索引段、TEMPORARY表示临时段等);BYTES:初始化为 0(此时无数据,物理占用为 0);BLOCKS:初始化为 0(Segment 占用的数据块数量,与BYTES关联:BYTES = BLOCKS * 数据块大小,GuassDB 默认数据块为 8KB);TABLESPACE_NAME:标记 Segment 所在的表空间(确定物理存储路径)。
2. 数据操作时:实时更新字节大小
当用户执行 INSERT/DELETE/UPDATE 等数据操作,或 ALTER TABLE 等结构调整时:
-
数据写入 / 删除会直接修改 DN 上 Segment 对应的物理数据文件(如新增数据块、释放空块);
-
GuassDB 的存储引擎会实时计算该 Segment 物理文件的最新占用大小,并同步更新 MY_SEGMENTS
中对应记录的 BYTES 和 BLOCKS 字段:
-
例如:插入 1000 行数据,占用 2 个 8KB 数据块,则
BLOCKS=2,BYTES=2*8192=16384(字节); -
例如:删除部分数据后,若释放了空数据块,
BLOCKS会减少,BYTES也会同步降低(注:部分场景下空块可能暂不释放,需手动执行VACUUM清理,此时BYTES可能暂时不变)。
-
3. 统计信息校准:确保大小准确性
除了实时更新,GuassDB 还会通过两种方式校准 MY_SEGMENTS 的元数据准确性:
- 自动统计(Auto ANALYZE):系统定期(默认配置)执行
ANALYZE操作,扫描各 Segment 的物理文件,核对并修正BYTES、BLOCKS等字段,避免因碎片、临时块等导致的大小偏差; - 手动统计(Manual ANALYZE):用户可执行
ANALYZE 表名手动触发统计,适用于数据量剧变后需要即时获取准确大小的场景。
四、查询逻辑:如何从 MY_SEGMENTS 读取表的字节大小?
MY_SEGMENTS 中的 BYTES 字段直接存储了单个 Segment 的物理占用字节数,而一张表的总字节大小 = 该表所有 Segment 的 BYTES 之和。
1. MY_SEGMENTS 核心字段说明(与 “字节大小” 相关)
| 字段名 | 含义说明 |
|---|---|
SEGMENT_NAME |
Segment 对应的对象名(如 “USER_INFO” 表名、“IDX_USER_INFO” 索引名) |
SEGMENT_TYPE |
Segment 类型(必须过滤为TABLE才是表的 Segment,排除索引 / 临时段等干扰) |
BYTES |
单个 Segment 的物理占用字节数(核心字段,直接对应 “字节大小”) |
BLOCKS |
Segment 占用的数据块数量(辅助验证:BYTES ≈ BLOCKS * 数据块大小,默认 8KB) |
TABLESPACE_NAME |
Segment 所在表空间(可定位物理存储路径) |
OWNER |
Segment 的所有者(避免查询其他用户的表) |
2. 实际查询表字节大小的正确逻辑
直接 select * from MY_SEGMENTS 会返回所有类型 Segment(表、索引、临时段等)的信息,需过滤 “表类型” 并汇总大小,例如:
-- 查询指定表(如USER_INFO)的总字节大小
select
segment_name as 表名,
sum(bytes) as 总字节数, -- 汇总所有DN上的Segment大小
sum(bytes)/1024/1024 as 总大小_MB -- 转换为MB更易读
from MY_SEGMENTS
where
segment_type = 'TABLE' -- 只保留表类型的Segment
and segment_name = 'USER_INFO' -- 指定表名(大写,GuassDB默认区分大小写)
and owner = 'USER1' -- 可选:过滤表所有者,避免歧义
group by segment_name;
补充:
GuassDB_T_1.2.1.SPC135.B002是企业版(T 代表企业版),MY_SEGMENTS的核心字段(BYTES、SEGMENT_TYPE)在 GuassDB 各版本中基本一致,原理通用
浙公网安备 33010602011771号