查询性能 Postgresql

Posted

技术标签:

【中文标题】查询性能 Postgresql【英文标题】:Query performance Postgresql 【发布时间】:2021-07-01 12:58:42 【问题描述】:

我们制作了一个控制台应用程序,它将更新表 b 上的 y 列。在服务器上运行这个查询,它很慢,我不知道为什么。表 t 大小为 21 GB,表 l 大小为 13 GB。

SELECT DISTINCT a.x,
                a.y 
FROM a 
JOIN b ON a.x = b.x 
-- x is uuid that we use on both tables
WHERE b.y IS NULL
  AND a.y IS NOT NULL
LIMIT 500;

到目前为止我尝试过的是;

    像这样在两个表上使用 where 语句创建索引

    创建索引 idx_name 在 b(x) 上 其中(y 为 NULL);

    创建索引 idx_name 在 (x) 上 其中 (y IS NOT NULL);

    使用 group_by 而不是 distinct

    尝试将最小的表连接到更大的表

你能帮帮我吗?

谢谢。

【问题讨论】:

edit您的问题并添加使用explain (analyze, buffers, format text)生成的execution plan(不是只是一个“简单”解释)为formatted text,并确保保留计划的缩进。粘贴文本,然后将``` 放在计划前一行和计划后一行。 添加执行计划。根据您的描述:您似乎没有尝试实现Index Only Scan。在CREATE INDEX 中查找选项INCLUDE。我想CREATE INDEX idx_name on a(x) INCLUDE (y) WHERE (y IS NOT NULL) 可以做到这一点 解释分析也花费了太多时间来返回结果 - 从 1 小时开始它仍在尝试 【参考方案1】:

尝试创建这两个多列covering indexes。

CREATE INDEX y_x_index ON a(y,x);
CREATE INDEX x_y_index ON b(x,y);

我猜第一个索引会对这些事情有所帮助:

    正在查找 a.y IS NOT NULL 行。 检索a.x 以用于加入 处理 SELECT DISTINCT 重复数据删除。索引的顺序适当,仅用于扫描。 无需查看主表,而是使用索引(这就是覆盖的意思)。

第二个索引会有所帮助

    正在检索 b.x 以用于加入。 正在寻找b.y IS NULL。 无需查看主表,而是使用索引。

您可以尝试切换第二个索引中列的顺序,看看是否更快。

并且,专业提示:请注意,没有 ORDER BY 子句的 LIMIT 子句会授予 postgreSQL 返回不可预测(非确定性)行集的权限。如果您想要一个可预测的 500 行,请输入 ORDER BY a.y, a.x。该子句中的列似乎颠倒了以匹配索引。 a.y 必须在索引中排在第一位,否则对于匹配 a.y IS NOT NULL 将无用。

【讨论】:

泰。我会尝试这些,但是当我在索引中使用 where 语句时,我没有让它更具体吗?我还检查了pg_stat_all_tables,看看两个表是否有死元组,但没有,没有。

以上是关于查询性能 Postgresql的主要内容,如果未能解决你的问题,请参考以下文章

openGauss维护管理之大小写敏感

个人书签

MongoDB如何优化查询性能?

CentOS 6安装PostgreSQL

如何查询Oracle性能监控

去IOE,MySQL完胜PostgreSQL