PostgreSQL9.6的新特性并行查询
发布日期:2021-05-08 12:24:41 浏览次数:19 分类:精选文章

本文共 2464 字,大约阅读时间需要 8 分钟。

PostgreSQL并行查询深度探索

并行查询参数概述

在PostgreSQL中,并行查询是一项强大的性能优化技术,尤其适用于处理大量数据和复杂查询。以下是影响并行查询的关键参数:

  • max_worker_processes:决定了数据库集群中可以启动的工作进程数量。需要注意的是,主库和standby库的参数值必须满足主从一致性要求,默认情况下设置为0表示禁用并行。

  • max_parallel_workers_per_gather:设置为1-4,控制每次查询可以分配的后台进程数量。这些worker主要来自max_worker_processes池。建议在OLTP环境中谨慎使用,因worker之间会竞争资源。

  • min_parallel_relation_size:启用并行查询的表大小下限。如果表大小小于此值,可能不会启用并行查询,但具体表现还需结合其他参数。

  • parallel_setup_costparallel_tuple_cost:这两个参数影响并行查询的启动和元组传输成本。较低的值有助于数据库更愿意使用并行查询。

  • force_parallel_mode:主要用于测试,强制启用并行查询。

  • parallel_workers:可用于表级设置,决定每个查询的并行度。

  • PostgreSQL优化器如何决定是否启用并行

    PostgreSQL优化器基于以下逻辑决定是否启用并行查询:

  • 确定可用worker进程数量:根据max_worker_processes设置确定。
  • 评估并行成本:优化器通过比较parallel_setup_cost和parallel_tuple_cost的值,决定是否启用并行。
  • 强制启用并行:通过force_parallel_mode参数强制设置。
  • 根据表级参数确定并行度:取parallel_workers和max_parallel_workers_per_gather中的最小值。
  • 自动确定并行度:当表未设置parallel_workers且表大小超过min_parallel_relation_size时,优化器会自动生成合适的并行度。
  • 并行顺序扫描测试

    什么是顺序操作?

    顺序操作类似于Oracle的全表扫描,PostgreSQL会按顺序读取整张表,逐行检查是否符合查询条件。对于单表查询,顺序操作的时间复杂度为O(n),通常在时间敏感的场景下更适合使用索引(O(log(n))),但索引的维护和存储可能带来额外开销。

    创建测试环境

    创建一个名为people的表,字段包括id(主键)和age:

    CREATE TABLE people (    id integer PRIMARY KEY NOT NULL,    age integer NOT NULL);

    插入测试数据

    插入1,000万行数据,每个人的年龄为1-100之间的随机数:

    INSERT INTO people    SELECT id, (random() * 100) :: integer AS age    FROM generate_series(1, 10000000);

    查询测试

    测试获取年龄为6岁的人:

    EXPLAIN ANALYZE SELECT * FROM people WHERE age = 6;

    分析查询计划

    查询计划显示使用了Seq Scan,实际时间为1579.476 ms。启用并行后:

    SET max_parallel_workers_per_gather TO 2;EXPLAIN ANALYZE SELECT * FROM people WHERE age = 6;

    此时查询时间降低到906.548 ms,表明并行查询有效减少了执行时间。

    聚合函数的并行计算测试

    重置环境

    SET parallel_tuple_cost TO DEFAULT;SET max_parallel_workers_per_gather TO 0;

    计算平均年龄

    未启用并行时的查询时间为905 ms:

    EXPLAIN ANALYZE SELECT avg(age) FROM people;

    启用并行后:

    SET max_parallel_workers_per_gather TO 2;EXPLAIN ANALYZE SELECT avg(age) FROM people;

    查询时间降低到181 ms,表明并行计算对聚合操作也有显著优化。

    join并行测试

    创建测试环境

    创建pets表并插入测试数据:

    CREATE TABLE pets (    owner_id int NOT NULL,    species character(3) NOT NULL);CREATE INDEX pets_owner_id ON pets (owner_id);INSERT INTO pets    SELECT (random() * 10000000) :: integer AS owner_id,           ('cat,dog')::text[], ceil(random() * 2)) AS species    FROM generate_series(1, 10000000);

    处理join查询

    未启用并行时的查询时间为5967.223 ms:

    EXPLAIN ANALYZE SELECT * FROM pets JOIN people ON pets.owner_id = people.id WHERE pets.species = 'cat' AND people.age = 18;

    启用并行后查询时间降低到1306 ms,表明并行查询对join操作也有显著优化。

    总结

    通过以上测试可以看出,PostgreSQL并行查询在特定场景下能显著提升查询性能。合理设置参数和监控查询行为是实现高性能的关键。此外,强制启用并行可能增加开销,因此需要根据具体需求进行权衡。

    上一篇:PostgreSQL中的多版本并发控制
    下一篇:pg_bulkload

    发表评论

    最新留言

    第一次来,支持一个
    [***.219.124.196]2025年04月16日 22时20分51秒