plsql - Oracle - 当我使用 EXISTS 时,关系运算符无效
问题描述
我收到了以下查询,当满足条件时,从表 et_fact_reclam_ter_his_misc 中删除返回的记录:
DELETE FROM et_fact_reclam_ter_his_misc
WHERE num_siniest || num_exped IN
(SELECT DISTINCT num_siniest || num_exped
FROM et_fact_reclam_ter_his_misc t1
WHERE NOT EXISTS (SELECT *
FROM et_fact_reclam_ter_misc t2
WHERE t1.num_siniest = t2.num_siniest));
我一直在搜索,发现使用EXISTS
而不是IN
会提高查询性能。但是我遇到了2个错误。第一个是当我将IN
运算符替换为时出现的错误消息EXISTS
:
DELETE FROM et_fact_reclam_ter_his_misc
WHERE num_siniest || num_exped EXISTS
(SELECT DISTINCT num_siniest || num_exped
FROM et_fact_reclam_ter_his_misc t1
WHERE NOT EXISTS (SELECT *
FROM et_fact_reclam_ter_misc t2
WHERE t1.num_siniest = t2.num_siniest));
ORA-00920: invalid relational operator
第二个是当我尝试将 a 嵌套SELECT
在 中时DELETE
,但返回的行数不同:
DELETE FROM et_fact_reclam_ter_his_misc
WHERE EXISTS
(SELECT FROM et_fact_reclam_ter_his_misc
WHERE num_siniest || num_exped IN
(SELECT DISTINCT num_siniest || num_exped
FROM et_fact_reclam_ter_his_misc t1
WHERE NOT EXISTS
(SELECT *
FROM et_fact_reclam_ter_misc t2
WHERE t1.num_siniest = t2.num_siniest)));
感谢您对提高查询性能的任何帮助
解决方案
你可以试试下面,不是连接字段的最佳方法,
DELETE FROM et_fact_reclam_ter_his_misc A
WHERE EXISTS
( SELECT 1 FROM
(SELECT DISTINCT num_siniest || num_exped
FROM et_fact_reclam_ter_his_misc t1) B
WHERE A.num_siniest|| A.num_exped = B.num_siniest || B.num_exped
AND NOT EXISTS (SELECT 1
FROM et_fact_reclam_ter_misc t2
WHERE B.num_siniest = t2.num_siniest));
似乎连接的列是数字,它会迫使 oracle 将其强制转换为 char,这可能会影响性能。如果您要处理大量记录,则低于一个应该会更快。
DELETE FROM et_fact_reclam_ter_his_misc A
WHERE EXISTS
( SELECT 1 FROM
(SELECT DISTINCT num_siniest, num_exped
FROM et_fact_reclam_ter_his_misc t1) B
WHERE A.num_siniest = B.num_siniest
AND A.num_exped = B.num_exped
AND NOT EXISTS (SELECT 1
FROM et_fact_reclam_ter_misc t2
WHERE B.num_siniest = t2.num_siniest));
DISTINCT 会矫枉过正,用 group by 代替肯定会好得多,所以最好的一个是:
DELETE FROM et_fact_reclam_ter_his_misc A
WHERE EXISTS
( SELECT 1 FROM
(SELECT num_siniest, num_exped,count(1)
FROM et_fact_reclam_ter_his_misc t1
group by num_siniest, num_exped) B
WHERE A.num_siniest = B.num_siniest
AND A.num_exped = B.num_exped
AND NOT EXISTS (SELECT 1
FROM et_fact_reclam_ter_misc t2
WHERE B.num_siniest = t2.num_siniest));
推荐阅读
- r - dplyr 中的滞后滚动间隔窗口
- c# - 为什么 StopForumSpam nuget 包不再工作了?
- excel - 将第二个文本列添加到与第一个文本列位于同一行的数据透视表
- angular - Angular 中的 FullCalendar - 获取选定的日期
- matlab - 关于 MPC 的 MATLAB 编码帮助
- api - 异构对象的 Restful API 设计
- google-cloud-platform - 覆盖查询结果后是否保留聚类?
- python - 我在解决 python 异常时遇到错误
- javascript - 在 javaScript 中使用 sessionStorage 存储数据
- r - 在 3D 中绘制一个简单的平面