我有一个包含4列的表
id | category | score | enabled
1 | news | 95 | t
id
-序列
category
-varchar
score
-浮动
enabled
-布尔
如果还有另一条得分更高的记录,我想将enabled
更新为False
。
例如,如果我有:
id | category | score | enabled
1 | news | 95 | t
然后,在执行一些操作后,将插入具有相同类别的新记录:
id | category | score | enabled
1 | news | 95 | t
2 | news | 100 | f
由于id=2
的得分较高,我想将enabled
的{{1}}更改为id=2
,并将True
的{{1}}更改为enabled
。
我想知道是否可以将这些操作合并为1个查询。现在,我进行2个id=1
查询以获取2条记录,然后在本地比较分数,然后更改False
值(如果需要)。
很简单,
SELECT
它可以工作,但是效率很低。有什么方法可以改善这些查询?
答案 0 :(得分:1)
您可以执行一次更新:
update the_table
set enabled = (score = t.max_score)
from (
select id, category, max(score) over (partition by category) as max_score
from the_table
where category = 'news'
) t
where t.id = the_table.id
and t.category = the_table.category;
这将在单个语句中为具有相同类别的所有行设置enabled
标志。
在线示例:https://rextester.com/DXR80618
如果您碰巧有一个行的同一类别的最高分得分相同,则以上语句将所有enabled
更改为true
。
例如
id | category | score
---+----------+------
1 | news | 95
2 | news | 100
3 | news | 100
如果您不想要那样,例如始终选择id
最低的那个作为已启用的行,您可以使用以下命令:
update the_table
set enabled = (rn = 1)
from (
select id, category,
row_number() over (partition by category order by score desc, id) as rn
from the_table
where category = 'news'
) t
where t.id = the_table.id
and t.category = the_table.category;