我有2张桌子
DEVICES
--------------------
DEVICE_ID MODEL_ID
1 A
2 B
3 C
4 D
CHANGE_VALUES
----------------------------------------
D_ID CHANGE_MODEL_ID
1 E
4 F
现在,我想更新MODEL_ID
表中DEVICES
的值,以了解表DEVICE_ID
中D_ID
中列出的所有CHANGE_VALUES
值。
我用来实现目标的SQL查询如下所示。但是,它似乎不是一个好的解决方案,因为对于DEVICE_ID
的每个值,都需要执行2个子查询。在包含~3k行的CHANGE_VALUES上运行它需要34秒,这似乎很长。
UPDATE devices dev
SET dev.model_id =
(SELECT c_value.change_model_id
FROM change_values c_value
WHERE dev.device_id = c_value.d_id
)
WHERE 1 IN
(SELECT COUNT(*)
FROM change_values c_value
WHERE dev.device_id = c_value.d_id
);
由于我是SQL的新手,我不知道是否有任何现有方法可以做同样的事情。所以我很想知道是否有更好的解决方案。
注意:我正在使用Oracle 10g
答案 0 :(得分:3)
您最大的问题是,您为COUNT(*)
中的每一行发出devices
- 这不是您实际需要做的;你需要一个EXISTS
条款。以下内容适用于任何RDBMS:
UPDATE Devices d SET model_id = (SELECT c.change_model_id
FROM Change_Values c
WHERE c.d_id = d.device_id)
WHERE EXISTS (SELECT *
FROM Change_Values c
WHERE c.d_id = d.device_id);
显然,假设你有Devices.device_id
的索引。 Change_Values.d_id
上的一个也可能加快速度。
答案 1 :(得分:0)
update devices a set model_id=(select change_model_id from change_values b where b.d_id=a.device_id)
where device_id in (select d_id from change_values)