如何复制巨大的postgres表?


29

我有巨大的postgres表(10GB数据-1.6亿条记录)。该表是静态的,并且没有对其执行任何写操作。我想复制它,执行写操作,重新索引它,然后通过一次快速事务删除旧的并将新的重命名为原始名称。

复制这么大表的最快方法是什么?

Answers:


55

通常,复制表的最快方法是:

CREATE TABLE table2 AS SELECT * FROM table1;

并行INSERT可能更快,但只有在磁盘子系统非常快的情况下(当数据在许多驱动器上交错时)。否则,它会变慢。

修改完后table2,它可以使用以下新名称:

BEGIN;
DROP TABLE table1;
ALTER TABLE table2 RENAME TO table1;
COMMIT;

DROP TABLE命令需要一个排他锁,以您可能希望的方式影响并发阅读器:

  • DROP 将等待其他事务在表上进行的所有未完成读取。
  • 同时,任何尝试读取该表的新事务都会将其置于等待状态,然后失败,因为原始表table1不再存在。该错误看起来像“无法打开与OID oid的关系”

为避免出现第二个问题,您可以重命名table1old_table1 而不是删除它,然后在这些读取器完成操作后,再将其删除到事务外部。因此,上面的序列将变为:

BEGIN;
ALTER TABLE table1 RENAME TO old_table1;
ALTER TABLE table2 RENAME TO table1;
COMMIT;
...
DROP TABLE old_table1;

2
谢啦。这正是我要寻找的解释。再次感谢!
Milovan Zogovic 2013年

如果在table2上定义了索引,则在重命名表后它们仍然可以工作吗?
BamaPookie

1
@BamaPookie可以查看完整的架构,包括索引,约束和默认值wiki.postgresql.org/wiki/Clone_schema
Timothy Vogel,
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.