当前位置: 首页 > news >正文

瀚高硬核助力 PG 社区:Postgres 19 迎来并行 TID 范围扫描,速度提升 3 倍

对于任何需要维护超大表(更新旧数据、分批删除、数据迁移)的 DBA 或开发者来说,使用 ctid(元组物理位置)将大表切分为多个小块进行处理是标准操作。然而,直到现在,这种操作都有一个巨大的痛点:它严格依赖单进程

随着最近的一个 Commit (0ca3b169) 合并入 PostgreSQL 19 (master 分支),TID 范围扫描(TID Range Scans)终于支持并行了

该功能由瀚高的 Cary Huang 提出并主导开发,由微软的 David Rowley 协助测试及审阅,并最终提交。他们密切合作以完善并行安全逻辑,确保工作进程正确处理扫描限制——最终促成了这个落地到 master 分支的健壮实现。

瀚高以“用开源链接世界”为使命,强调开源技术在数据库基础软件领域的核心作用,致力于通过共享和合作,推动行业发展,同时链接和赋能全球用户。开源技术是中国软件技术发展的必由之路,瀚高作为亚太地区 PostgreSQL 国际社区顶级贡献者之一,长期深度参与 PostgreSQL 国际社区发展与建设。自 2025 年 7 月以来,瀚高被 PostgreSQL 社区采纳的贡献就已超过 2000 行代码。

根据基准测试,新特性的速度提升高达 3 倍

1. 核心痛点:规划器(Planner)的权衡

Postgres 自版本 14 起就支持了 TID Range Scans。这允许你基于物理块号扫描表的特定切片:

SELECT * FROM my_large_table WHERE ctid >= '(0,0)' AND ctid < '(10000,0)';

这是像 AWS DMS 这样的工具或逻辑复制初始化器拆分海量表的标准方式。问题在于,直到现在这种扫描节点严格来说都是单工作进程(single worker) 的。

这迫使 Postgres 查询规划器陷入了两难境地。当你在大数据集上运行查询时,规划器必须在以下两者之间做出选择:

  • TID Range Scan: I/O 高效(只读取你请求的块),但是单工作进程。

  • Parallel Seq Scan(并行顺序扫描): CPU 高效(占用所有 CPU 内核),但 I/O 浪费(可能会为了过滤而读取超出你范围的块)。

规划器经常会错误地选择并行顺序扫描,CPU 收益似乎超过了 I/O 损耗带来的负面影响。这导致数据库为了利用可用的工作进程,读取了比必要多得多的数据。

2. 修复方案:并行性与可变分块

由 Cary Huang 开发并由 David Rowley 提交的代码,引入了允许 Tid Range Scan 参与并行查询计划的基础架构。该逻辑有效地将块范围分配给可用的并行工作进程。不再是一个进程从块 0 扫描到 N,多个工作进程可以并发地获取数据块。

实现(约 500 行代码)重用了并行顺序扫描中的“块分块(block chunking)”逻辑。但它不仅仅是将块范围平均分配给工作进程,因为如果表的某个部分数据密度更高,这种简单分配可能导致负载不均衡。

相反,它使用了衰减块大小策略 (decaying chunk size strategy):

  • 大块开始 (Large Start): 工作进程开始时领取大块的块,以最大限度地减少共享状态上的锁定开销。
  • 逐渐减小 (Tapering Down): 随着扫描的进行,分块大小会缩小。
  • 颗粒化结束 (Granular Finish): 到扫描结束时,工作进程每次只领取 1 个块。

这种“缓慢减少”确保了我们不会最后只剩下一个工作进程在处理一个巨大的最终块,而其他工作进程却闲置着。它强制所有进程大致在同一时间跨过终点线。

3. 基准测试数据

为了看到实际效果,我创建了一个包含 1000 万行的表 bench_tid_range,并使用 ctid 范围条件对表的前 50% 运行了 count(*) 查询。

测试环境:

  • 数据量:1000 万行
  • 查询:SELECT count(*) FROM bench_tid_range WHERE ctid >= '(0,0)' AND ctid < '(41667,0)'
环境 工作进程数 (Workers) 执行时间 (中位数) 加速比
Before (Pg 18) 0 448 ms 1.00x
After (Pg 19) 0 435 ms 1.03x
After (Pg 19) 1 238 ms 1.88x
After (Pg 19) 2 174 ms 2.58x
After (Pg 19) 3 151 ms 2.97x
After (Pg 19) 4 150 ms 2.98x
After (Pg 19) 5 147 ms 3.05x
After (Pg 19) 6 143 ms 3.14x
After (Pg 19) 7 147 ms 3.04x
After (Pg 19) 8 147 ms 3.04x

1.png

我们可以看到,仅仅启用 1 个工作进程(这实际上给了我们 2 个扫描进程:Leader + 1 个 Worker),执行时间就大幅下降。对于这个特定的工作负载,“最佳平衡点”似乎在 2-3 个工作进程左右。

4. 为什么不直接用“并行顺序扫描”?

你可能会问:“为什么 Postgres v18 不直接选择并行顺序扫描?用 4 个工作进程扫描整个表难道不比用 1 个进程扫描半个表快吗?”

我通过强制设置 enable_tidscan = off 并使用 4 个工作进程测试了这一点:

  • 执行时间: ~230 ms。
  • I/O: 访问了所有 ~83k 个页面。

新的并行 TID 范围扫描(~150 ms)仍然比暴力/强制的并行顺序扫描快 35%,而且它产生的 I/O 负载只有后者的一半(只访问了 ~41k 个页面)。这可谓两全其美:快速的执行时间(并行)和高效的资源使用(类似索引的范围界定)。

5. 这对工具意味着什么

如果你维护在 Postgres 实例之间移动数据的内部脚本,你可能编写了手动计算块范围并将巨大的表划分为块、然后生成进程来运行它们的代码。

随着 PostgreSQL 19 的推出,这种复杂性可能可以被删除了。你可以发出更广泛的 TID 范围查询,并相信规划器会有效地在集群的 I/O 和 CPU 资源之间分配工作。

6. 如何复现测试

这是设置测试表和运行基准测试的 SQL:

-- 1. 创建表
DROP TABLE IF EXISTS bench_tid_range;
CREATE TABLE bench_tid_range (id int, payload text);-- 2. 插入 10M 行以生成 ~41k 个页面
INSERT INTO bench_tid_range
SELECT x, 'payload_' || x
FROM generate_series(1, 10000000) x;-- 3. Vacuum 以设置可见性映射并冻结(对于稳定的基准测试很重要)
VACUUM (ANALYZE, FREEZE) bench_tid_range;-- 4. 为会话启用并行
SET max_parallel_workers_per_gather = 4; -- 尝试 2, 4, 8
SET min_parallel_table_scan_size = 0;    -- 即使对于较小的表也强制并行扫描-- 5. 运行查询
EXPLAIN (ANALYZE, BUFFERS)
SELECT count(*)
FROM bench_tid_range
WHERE ctid >= '(0,0)' AND ctid < '(41667,0)';

7. 结论

这是一项令人欣喜的“底层”改进。它或许不会改变您日常的临时查询,但对于构建自定义数据维护脚本的数据库管理员和开发人员而言,并行执行基于 TID 的扫描功能是优化工具包中一项强大的新工具。

8. 参考

本文部分内容是来自 Grant Zhou 和 Robins Tharakan 撰写的英文博客。

  • 提交 0ca3b169:https://git.postgresql.org/gitweb/?p=postgresql.git;a=commitdiff;h=0ca3b16973a8bb1c185f56e65edcadc0d9d2c406
  • 讨论贴:https://www.postgresql.org/message-id/flat/18f2c002a24.11bc2ab825151706.3749144144619388582%40highgo.ca
  • https://hornetlabs.ca/2025/12/08/speeding-up-large-table-scans-with-parallel-tid-ranges-in-postgresql-19/
  • https://www.thatguyfromdelhi.com/2025/12/3x-faster-tid-range-scans-postgres-19.html
http://www.jsqmd.com/news/78074/

相关文章:

  • MinerU软件版本升级完全指南:实现平滑系统迁移
  • Android 14媒体访问权限适配终极指南:PictureSelector Library全面更新
  • 2025 年 12 月图书出版机构权威推荐榜:医学教材、学术专著、儿童读物等全品类出版服务深度解析与口碑之选 - 品牌企业推荐师(官方)
  • AirConnect终极指南:轻松实现AirPlay音频跨设备播放
  • Wasmer WebAssembly运行时终极指南:从零到实战部署
  • 9款免费AI论文神器:带真实参考文献,30分钟出查重低原创高初稿! - 麟书学长
  • TIOBE 编程社区 查看各种编程语言流行程度和趋势的社区
  • 打印机双面扫描文件保存到windows11家庭版电脑,提示出错:正在连接服务器,服务器响应错误
  • DataRoom大屏设计器:零代码构建企业级数据可视化的完整解决方案
  • 计算机毕业设计 基于Python的电商用户行为分析强大的系统 Django 大素材毕业设计 Hadoop毕业设计选题【附源码+文档报告+安装调试】
  • 从拖延到高效:当课程论文写作遇上宏智树AI辅导新范式
  • 重口味解馋小零食测评:我最近最上头的「辣人辣椒酥」怎么吃最爽? - AIEO
  • 荣耀路由Pro(WS851)固件下载:提升网络性能的完整指南
  • 2025年铜销打包机实力厂家推荐榜单:废铜打包机‌/铜屑打包机‌/铜刨花打包机源头厂家精选 - 品牌推荐官
  • Java 8都出了这么多年,Optional还是没人用?到底卡在哪了?
  • Zotero-reference插件:重新定义学术文献管理新体验
  • VRM与VRChat模型转换终极指南:免费工具让新手快速上手!
  • CMD299K4:18-40 GHz 低噪声放大器, 现货库存
  • 医学考研资料怎么选?首选昭昭医考!超全攻略帮你避坑 - 品牌测评鉴赏家
  • Python进阶之路:模块、包与异常处理的实战指南
  • 突破 LLM 极限!n8n + MemMachine 打造“无限流”小说生成器
  • 全国腹膜后肿瘤三大权威专家推荐 | 聚焦“南陆”陆维祺教授 - 速递信息
  • 抖音碰一下买单是什么?本地生活线下引流神器!
  • 无锡旅行社推荐:行业展望数智化 + 新业态,万达国旅领跑未来 - 品牌智鉴榜
  • 2025年12月昭昭医考视频评测:模块化切片学习法助力医学考试备考 - 品牌测评鉴赏家
  • 2025年飘雪机制造商权威推荐榜单:小型飘雪机/人工飘雪机/大型飘雪源头厂家精选 - 品牌推荐官
  • 【选购建议】雷达料位计/磁致伸缩液位计推荐国产品牌江苏万德和河北光科 - 品牌推荐大师
  • 洗面奶哪个牌子最好用?熬夜党必备!2025洗面奶品牌排行榜前十名,温和净肤不刺激 - 速递信息
  • 2025年上海行星减速机定制生产厂家推荐,靠谱的行星减速机厂 - 工业推荐榜
  • 2025年空心轴订做厂家推荐榜单:链接杆‌/不锈钢棍‌/喷砂棍源头厂家精选 - 品牌推荐官