My_Table会是这样的:
user_id shared_field bool_field
------- ------------ ----------
1 abc null
2 def null
3 ghi Y
4 ghi null
5 ghi null
6 abc Y
7 jkl null
如果bool_field更改为与其他用户共享相同shared_field的用户(例如上面的user_id 3,4和5),则只有该用户应该具有“Y”。其余的应该在bool_field列中具有空值。例如,如果user_id 4现在应该具有'Y',我必须将user_id 4的bool_field更改为'Y',并确保user_id 3和5的bool_field值为null。
如果用户不与其他任何人共享shared_field值,则该bool_field应为null(如上面的user_id 1和2中所示)。
更新:添加了几行以显示多个user_id可以共享给定的shared_field(例如,1和6都有'abc'; 3,4和5都有'ghi' - 只有一个'abc'用户应该有'Y',只有一个'ghi'用户应该有'Y'等等,而其余用户的bool_field列中为null; user_ids不共享shared_field值,例如user_ids 2和7,它们的bool_field列中都应该为null。)清除为泥,对吧? ;)
此声明有效:
UPDATE my_table
SET bool_field = (CASE
WHEN user_id = 4 THEN 'Y'
ELSE NULL
END)
WHERE shared_field = 'ghi'
AND (SELECT COUNT(shared_field)
FROM my_table
WHERE shared_field = 'ghi') > 1;
问题:在没有提前知道shared_field值的情况下,我是否可以通过某种方式完成同样的事情?例如(当然这不起作用) - 更新:“当然”意味着我知道这不起作用,因为它不是正确的Oracle语法!重点是要了解我正在尝试做什么。
UPDATE my_table
SET bool_field = (CASE
WHEN user_id = 4 THEN 'Y'
ELSE NULL
END)
WHERE shared_field = (SELECT shared_field FROM my_table WHERE user_id = 4) as sharedVal
AND (SELECT COUNT(shared_field)
FROM my_table
WHERE shared_field = sharedVal) > 1;
更新:这是一个常规的SQL语句 - 我无法使用存储过程。
答案 0 :(得分:1)
首先,告诉我们它是如何工作的,通常很有帮助,而不是说某些事情并没有起作用。例如,您发布的查询似乎有语法错误(as sharedVal
无效,因为您无法为您在SELECT
列表中计算的表达式分配别名。但是,不清楚是否"不起作用"意味着你得到语法错误(我们可以相对容易地使用错误消息进行调试)或者是否意味着查询运行但是没有做你想要的(我希望查询能做到这一点)语法错误已得到纠正)在这种情况下,了解查询如何做你想做的事情会有所帮助。
我希望像
这样的东西UPDATE my_table a
SET bool_field = (CASE WHEN user_id = 4
THEN 'Y'
ELSE NULL
END)
WHERE shared_field = (SELECT shared_field
FROM my_table b
WHERE b.user_id = 4)
AND EXISTS( SELECT 1
FROM my_table c
WHERE a.shared_field = c.shared_field
AND a.user_id != c.user_id )
假设user_id
是主键,开始工作。
答案 1 :(得分:0)
自从我使用Oracle以来已经有一段时间了,所以请检查以确保此查询返回您要更新的记录列表:
SELECT *
FROM my_table m
WHERE EXISTS (SELECT 1
FROM my_table
WHERE shared_field = m.shared_field
HAVING COUNT(shared_field) > 1);
如果是这样,那么这应该有效:
UPDATE my_table
SET bool_field = (CASE
WHEN user_id = 4 THEN 'Y'
ELSE NULL
END)
WHERE EXISTS (SELECT 1
FROM my_table
WHERE shared_field = m.shared_field
HAVING COUNT(shared_field) > 1);
你也可以尝试这个WHERE
条款:
WHERE shared_field IN (SELECT shared_field
FROM my_table
GROUP BY shared_field
HAVING COUNT(shared_field) > 1);