Postgresql 在红移中优化大型表的更新

Postgresql 在红移中优化大型表的更新,postgresql,amazon-redshift,Postgresql,Amazon Redshift,我有一张大桌子,上面有14亿条记录。每天我都要根据另一个较小但不是很小的表中的某些条件,使用如下update语句来更新这个大表的一些记录: UPDATE my_large_table set a_field_that_needs_to_be_updated = 1 WHERE join_field IN (SELECT join_field FROM another_table where some_other_conditions 这有时需要超过30分钟,这是我们的超时值,因此作业将被中止

我有一张大桌子,上面有14亿条记录。每天我都要根据另一个较小但不是很小的表中的某些条件,使用如下update语句来更新这个大表的一些记录:

UPDATE my_large_table set a_field_that_needs_to_be_updated = 1 WHERE join_field IN (SELECT join_field FROM another_table where some_other_conditions
这有时需要超过30分钟,这是我们的超时值,因此作业将被中止

一个简单的解决方案是增加超时值,但这不是我想要的路线。 另一种优化方法是在两个表模式中都使用join_字段作为distkey,但由于存在更常见的join用例,因此另一个字段被设置为distkey。
所以我想知道是否可以将这个查询分解为多个分区查询。join_字段实际上是一个字母数字散列值,我可以只看字段的第一个字符,然后使用LIKE将语句分为36个较小的部分0到9和A到Z。但我想知道是否有更好的办法

是的,我想说的是,你提到的分块查询是你最好的选择。通常,最快的方法是将OFFSET和LIMIT on与ORDER BY结合起来定义块,但使用非常大的有序OFFSET值本身可能是一个性能问题,因为它必须先计算整个订单,然后再计算LIMIT和OFFSET,特别是考虑到表中记录的数量

然而,由于您声明已经通过一个可以唯一迭代的哈希值对它们进行了分区,因此我将简单地使用它作为分块机制——它是内置的,并且应该为您提供更小的分块。您可以考虑通过前面提到的机制进一步细分这些块,如果它们仍然太大而不能很好地执行。

请注意,您可能需要在哈希列上有索引,以便它能够快速找到它们,尽管从纯Postgres的角度来看,如果查询计划器决定需要返回太多行,并且红移可能会有额外的差异,则可能不会使用索引

进一步优化,可以考虑多线程同时进行多个更新。我经常为此使用该工具,因为它允许对shell命令进行快速简单的多线程处理。这可以与psql客户端结合使用,正如我所知,它在红移中受支持

注:

最终,我认为最好的总体方案是为哈希值的每个第一个字符都有单独的表,每个表都从主表继承。这使得每个表都可以在更新中单独处理,而无需首先进行大型筛选操作等,但您仍然可以使用父表查询所有表,即它不应该真正影响现有的SELECT语句

然而,这肯定是一个更大的任务,现在可能不可行,如果你要做这样的事情,你会想和查询计划员核实一下,等等。这确实是一个改进,没有红移的具体原因,这不是一个好主意。我纯粹是从博士后的角度讲的