一、PostgreSQL分区表实现逻辑
1.1. 分区类型详解
PostgreSQL支持两种主要的分区类型:
• 范围分区(Range Partitioning)
根据表中某一列的值范围将表分割成若干个分区。例如,我们可以按照时间字段(如日期)创建按年、季度或月份的范围分区。
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61467-0-6-0-67a957c0_9c60_4b95_ad3f_64a3ac10c669.png?auth_key=1739721599-0-0-d8e186e94bfa655bc3ed5148a968bc0c)
• 列表分区(List Partitioning)
根据某一列的特定值列表来划分分区。例如,可以根据国家/地区的枚举值进行列表分区。
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61468-0-6-0-67a957f0_2128_4989_93d1_651bac10c669.png?auth_key=1739721599-0-0-5cd54ffd67435f5e58c119e832f2221a)
• hash分区(hash Partitioning)
根据某一列的特定值列表来划分分区。例如,可以根据国家/地区的枚举值进行列表分区。
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61469-0-6-0-67a95812_2874_4b1f_b2d4_6512ac10c669.png?auth_key=1739721599-0-0-4fb9d39ea4a50d3fbbfb46e569587088)
查看表结构
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61470-0-6-0-67a9582d_0a40_4a12_96f7_649eac10c669.png?auth_key=1739721599-0-0-d1e6d394e965407b2d24d1b514a869a9)
插入数据,查看数据分布
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61471-0-6-0-67a9583e_7534_45ec_bd8b_648cac10c669.png?auth_key=1739721599-0-0-3f759d9fbac026d433c87520ac92e789)
二、分区表维护操作
2.1 添加分区
示例:添加range分区
![](https://pic3.zhimg.com/v2-115e2d995bf1f7c1347ba4b90386cf2c_1440w.jpg)
2.2 删除分区
![](https://pic2.zhimg.com/v2-e41d4018d4aa5688771453542e87a0bf_1440w.jpg)
2.3 ATTACH分区
ATTACH操作:ATTACH操作用于将一个已存在的表作为分区添加到一个分区表中。这样做的好处是可以将预先填充好数据的表作为分区快速加入到分区表体系中,或者在需要调整分区布局时将一个表转换为分区表的分区。
![](https://pic2.zhimg.com/v2-73aa14421869f616a05882bb309e6be1_1440w.jpg)
其中:
• partitioned_table:已存在的分区表名。
• new_partition_table:要作为分区添加的已存在的表名,该表应具有与partitioned_table相同的结构,并且其数据应符合所指定的分区范围。
• FOR VALUES IN (partition_range):指定新分区所对应的分区键值范围。partition_range应与分区表的分区策略相匹配。
示例:
假设有一个按年份分区的销售表sales,现在有一张名为sales_2024的表,里面存储了2024年的销售数据,希望将其作为sales表的一个分区。
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61472-0-6-0-67a95857_239c_4ddf_bcfa_64a7ac10c669.png?auth_key=1739721599-0-0-a8b22d289f5027769322dd5ddcd6c84c)
-- 假设sales_2024表已存在且结构与sales表相同,数据均为2024年的销售记录
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61473-0-6-0-67a95871_e92c_4fb1_8e7b_64b2ac10c669.png?auth_key=1739721599-0-0-5a48e7d3991fe523f02c8acc60af43c8)
2.3 DETACH分区
DETACH操作:DETACH操作用于从分区表中移除一个现有的分区。
这通常在需要临时独立处理某个分区的数据(如备份、迁移、清理等)或者调整分区布局时使用。
语法:
ALTER TABLE partitioned_table DETACH PARTITION existing_partition;
其中:
• partitioned_table:已存在的分区表名。
• existing_partition:要从分区表中分离出去的现有分区表名。
示例:假设要将sales表中存储2023年销售数据的分区sales_2023分离出来,以便单独进行数据清理。
![](https://pic1.zhimg.com/v2-0aaf10695a5745683957d27f092d667a_1440w.jpg)
注意事项:
• ATTACH与DETACH操作都会立即生效,对分区表结构进行更改。在执行这些操作时,应确保没有正在进行的事务依赖于被操作的分区。
• 分离出来的分区表仍保留其数据,可以独立进行查询、更新等操作。但在DETACH之后,该分区不再受分区表的查询优化等特性影响。
• 在ATTACH操作中,新分区表的数据应严格符合所指定的分区范围,否则可能会导致数据完整性问题或查询错误。
• 对于DETACH操作,确保在分离后对分区表的查询不受影响,可能需要调整查询条件或创建合适的索引。
2.4 自动扩建分区
请读者使用pg_partman插件完成
三、分区表优化示例
在处理海量数据的场景下,PostgreSQL的分区表功能成为了提升查询性能和管理效率的关键利器。案例背景一家电子商务公司拥有一个庞大的订单表,表中记录了历年来的所有订单数据。随着业务的发展,订单表的数据量已经达到了数十亿行,导致查询性能严重下滑,尤其在处理特定时间段的报表查询时,响应时间变得极其漫长。问题分析
1. 查询性能低下:由于订单表庞大,任何涉及到全表扫描的查询都会花费很长时间。
2. 数据维护困难:数据清理和归档工作复杂,难以对老旧数据进行高效管理。
分区表优化方案基于上述问题,我们采用了PostgreSQL的范围分区功能对订单表进行优化。
步骤一:创建分区表
首先我们决定按年份对订单表进行范围分区,每年一个分区:
![](https://bexp.135editor.com/uploadword/15351900/202502/67a95881_8618_4051_be48_6468ac10c669.png?auth_key=1739721599-0-0-613d467ecd33b2ee0528b93c22ba12e6)
-- 创建2010年至2022年的分区
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61474-0-6-0-67a958a5_bf9c_4f9a_bd00_6482ac10c669.png?auth_key=1739721599-0-0-774a44f496c54c00e4c2d766f7662174)
--查看当前分区
![](https://bexp.135editor.com/uploadword/15351900/202502/67a958b2_6fac_45d1_a6a4_64edac10c669.png?auth_key=1739721599-0-0-bf62b6a7d98b504901760207456b364f)
--模拟数据
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61475-0-6-0-67a958c4_eb58_4ad0_8ccf_646cac10c669.png?auth_key=1739721599-0-0-a9630649b98aa7bda99e88257e58e8bd)
步骤二:创建普通表
![](https://pic2.zhimg.com/v2-8b88d5aa9b0fe259cb326b1a488d631b_1440w.jpg)
步骤三:对比性能
1)非分区表
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61477-0-6-0-67a958f5_3a84_4c22_89e3_64a8ac10c669.png?auth_key=1739721599-0-0-368c67e97e4a804f194365042e9e2033)
2) 分区表
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61476-0-6-0-67a958db_fb10_4fe7_9920_652cac10c669.png?auth_key=1739721599-0-0-31dd46f600c308a50cceae95fe8508ab)
对比以上两个执行计划
![](https://bexp.135editor.com/uploadword/15351900/202502/bige-2750882-61478-0-6-0-67a9591e_8c44_45f2_81e4_6502ac10c669.png?auth_key=1739721599-0-0-7281724d3ef5739aebbfb3763ef3f114)
效果验证优化后,查询性能有了显著提升,因为查询仅针对特定年份的分区,避免了对整个大表的扫描。此外,数据维护工作也变得更加方便,可以直接操作单个分区进行数据清理和归档。
今天就分享到这里,希望对你们有帮助!感恩遇见!感谢有你们!码字不易,如果喜欢希望能够“点赞➕收藏➕关注”,我们建了一个免费技术/资源分享社群、大家一起交流!可直接扫下面二维码添加我,请备注{夏天}拉你入群,希望可以帮到你!
声明:
1、2群已满500人!
3群刚开始筹建,满200人后不在邀请新卡友【有想一块交流的可以赶快】
添加请备注来意
(禁广告!禁广告!禁广告!发现秒踢拉黑!)