在 Postgresql 中的多个列上执行 WHERE IN

问题描述 投票:0回答:4

我有一个表“answers”,其中包含索引的“problem_id”整数列、“times_chosen”整数列和一个 varchar 的“option”列。目前,“选项”列的唯一值是“A”、“B”、“C”和“D”,尽管这些值稍后可能会扩展。当我知道每个答案的 Problem_id 和选项时,我想将许多(50-100)个答案的“times_chosen”值加一。

所以我需要一个类似的查询:

UPDATE answers
SET times_chosen = times_chosen + 1
WHERE (problem_id, option) IN ((4509, 'B'), (622, 'C'), (1066, 'D'), (4059, 'A'), (4740, 'A')...)

这可能吗?

编辑添加:事实证明确实如此,使用我发明的确切语法!

sql postgresql
4个回答
41
投票

您可以加入某种虚拟表:

SELECT * FROM answers
JOIN (VALUES (4509, 'B'), (622, 'C'), (1066, 'D'), (4059, 'A'), (4740, 'A')) 
    AS t (p,o)
ON p = problem_id AND o = option

您可以使用 UPDATE 执行类似的操作。


22
投票

应该是的,至少我之前在其他 SQL 中做过。

你尝试过吗?您可以使用

SET times_chosen = times_chosen

进行测试

5
投票

如果先将数据转换为数组,则可以执行此操作:

UPDATE answers
SET times_chosen = times_chosen + 1
WHERE ARRAY[problem_id::VARCHAR,option] IN ('{4509,B}', '{622,C}', ... )

但是,这将非常低效,因为它无法使用索引。 使用 @Frank Farmer 建议的 JOIN 是一个更好的解决方案:

UPDATE answers a
SET times_chosen = times_chosen + 1
FROM (VALUES (4509,'B'), (622,'C') ...) AS x (id,o)
    WHERE x.id=a.problem_id AND x.o=a.option;

-5
投票

您可能正在寻找

SELECT * FROM foo, bar WHERE foo.bob = "NaN" AND bar.alice = "Kentucky";

风格语法。 本质上,您使用 tablename.rowname 来指定您要查找的单个字段。 为了正确排列所有内容,您添加 WHERE 子句以确保主键匹配:

...WHERE foo.primarykey = bar.primarykey

或类似的。 您最好查找内部联接。

© www.soinside.com 2019 - 2024. All rights reserved.