我有下表:
+----+--------+-----+
| id | fk_did | pos |
+----+--------+-----+
此表包含数百行,每一行都使用 fk_did
引用另一个表。 pos
中的值当前始终为零,我想更改它。
基本上,对于每组 fk_did
,pos
列应该从零开始并按升序排列。行的排序方式无关紧要。
我想要获得的示例输出(select * from table order by fk_did, pos
):
+----+--------+-----+
| id | fk_did | pos |
+----+--------+-----+
| xx | 0 | 0 |
| xx | 0 | 1 |
| xx | 0 | 2 |
| xx | 1 | 0 |
| xx | 1 | 1 |
| xx | 1 | 2 |
| xx | 4 | 0 |
| xx | 8 | 0 |
| xx | 8 | 1 |
| xx | 8 | 2 |
+----+--------+-----+
- 不得有两行具有相同的
fk_did
和pos
组合 pos
对于每个fk_did
必须升序
- 如果有一行
pos
> 0,则还必须有一行具有相同的fk_did
和较低的pos
。
这可以通过单个更新查询完成吗?
最佳答案
您可以使用窗口函数执行此操作:
update the_table
set pos = t.rn - 1
from (
select id,
row_number() over (partition by fk_id) as rn
from the_table
) t
where t.id = the_table.id;
pos
的顺序将或多或少是随机的,因为没有 order by
,但你说过这无关紧要。
这假设 id
是唯一的,如果不是,您可以使用内部列 ctid
代替。
关于用于在组内创建升序值的 SQL 查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35384035/