如何填充可为空的整数列并将其转换为 Postgresql 中的串行主键?

n10*_*000 0 postgresql primary-key

我的表包含一个gid可以为空的整数列 ( ):

 gid | value
-------------
  0  |   a
     |   b
  1  |   c
  2  |   d
     |   e
Run Code Online (Sandbox Code Playgroud)

现在我想将该gid列更改SERIAL为主键列。这意味着用新整数填充空槽。现有的整数必须保持原位。所以结果应该是这样的:

 gid | value
-------------
  0  |   a
  3  |   b
  1  |   c
  2  |   d
  4  |   e
Run Code Online (Sandbox Code Playgroud)

我只是想不出正确的 SQL 命令来进行转换。代码示例将不胜感激...

a_h*_*ame 6

A serial“只是”一个从序列中获取默认值的列。假设您的表已命名,n1000则以下内容将执行您想要的操作。

您需要做的第一件事是创建该序列:

create sequence n1000_gid_seq;
Run Code Online (Sandbox Code Playgroud)

然后,您需要将其设为该列的“默认值”:

alter table n1000 alter column gid set default nextval('n1000_gid_seq');
Run Code Online (Sandbox Code Playgroud)

要真正创建“序列”,您还需要告诉序列它与列相关联:

alter sequence n1000_gid_seq owned by n1000.gid;
Run Code Online (Sandbox Code Playgroud)

然后您需要推进序列,以便下一个值不会与现有值冲突:

select setval('n1000_gid_seq', (select max(gid) from n1000), true);
Run Code Online (Sandbox Code Playgroud)

最后你需要更新表中的缺失值:

update n1000 
  set gid = nextval('n1000_gid_seq')
where gid is null;
Run Code Online (Sandbox Code Playgroud)

完成此操作后,您可以将列定义为 PK:

alter table n1000 
   add constraint pk_n1000
   primary key (gid);
Run Code Online (Sandbox Code Playgroud)

当然,如果您关闭了自动提交,则需要commit所有这些。