Answers:
有什么问题:
ALTER TABLE foo ADD column bar bigserial;
将自动填充唯一值(从1开始)。
如果要为每个现有行都提供一个数字,则必须更新表中的每一行。还是不?
如果表无法重用死元组或数据页上的可用空间,则该表的大小将膨胀到其两倍。FILLFACTOR
小于100的随机元组或分布在表上的随机死元组可能会大大提高操作性能。否则,您可能要VACUUM FULL ANALYZE
稍后再运行以恢复磁盘空间。不过,这不会很快。
pgstattuple
您可能对此扩展感兴趣。它可以帮助您收集表中的统计信息。要了解死元组和可用空间,请执行以下操作:
每个数据包一次安装扩展程序:
CREATE EXTENSION pgstattuple;
呼叫:
SELECT * FROM pgstattuple('tbl');
如果您有能力创建一个新表,该表会因视图,外键,...而中断。
创建旧表的空副本:
CREATE new_tbl AS
SELECT *
FROM old_tbl
LIMIT 0;
添加bigserial列:
ALTER new_tbl ADD column bar bigserial;
从旧表中插入数据,自动填充bigserial:
INSERT INTO new_tbl
SELECT * -- new column will be filled with default
FROM old_tbl
ORDER BY something; -- or don't order if you don't care: faster
INSERT的SELECT中缺少新的bigserial列,该列将自动填充为其默认值。您可以拼出所有列,并添加nextval()
到SELECT
列表中以达到相同的效果。
确保所有数据都在新表中。
添加索引,约束,你在旧表有触发器现在。
DROP TABLE old_tbl;
ALTER TABLE new_tbl RENAME TO old_tbl;
总体上可能要快得多。这样就为您提供了一个没有任何膨胀的原始表(和索引)。
您需要可用磁盘空间(大约为旧表的大小,具体取决于表的状态)作为摆动空间。但是由于表膨胀,您可能需要使用第一种简单方法。同样,详细信息取决于表的状态。
fsync
的错误