oracle select 今天记录但排除前几天可能存在的记录
oracle select records today but exclude those which may exist in the previous days
oracle 中的table 中应该存在两条记录,一条来自请求,一条来自响应。
我想 select 所有今天的记录,但问题是另一对可能存在于前两天或更长时间。
怎么保证返回的记录只有1条,前几天不存在
select A.referenceNum, A.datetime, A.Type from table A where A.datetime >= sysdate - 1
为了形象化,我只想select reference num 789ef.
ReferenceNum DateTime Type
123ab (今天到今天)请求
123ab (日期到今天)响应
456cd (日期到今天)请求
456cd (datetoday-2)响应
789ef (日期到今天)请求
使用NOT EXISTS
运算符
SELECT A.referenceNum, A.datetime, A.Type
from table A
where A.datetime >= sysdate - 1
AND NOT EXISTS (
SELECT null FROM table B
WHERE A.referenceNum = B.referenceNum
AND b.datetime < a.datetime
)
SELECT referenceNum
FROM A A1
WHERE TRUNC(A1.datetime) > TRUNC(sysdate)-1
AND A1.Type = 'Request'
AND NOT EXISTS
(SELECT 1
FROM A
WHERE TRUNC(A.datetime) >= TRUNC(sysdate)-1
AND A.Type = 'Response'
AND A.referenceNum = A1.referenceNum
)
您可以使用分析函数在一次 table 扫描中完成(与使用 NOT EXISTS
相比,后者将使用两次 table 扫描):
SQL Fiddle
Oracle 11g R2 模式设置:
CREATE TABLE table_name ( ReferenceNum, DateTime, Type ) AS
SELECT '123ab', SYSDATE, 'Request' FROM DUAL UNION ALL
SELECT '123ab', SYSDATE, 'Response' FROM DUAL UNION ALL
SELECT '456cd', SYSDATE, 'Request' FROM DUAL UNION ALL
SELECT '456cd', SYSDATE - 2, 'Response' FROM DUAL UNION ALL
SELECT '789ef', SYSDATE, 'Request' FROM DUAL;
查询 1:
SELECT ReferenceNum
FROM (
SELECT ReferenceNum,
COUNT( CASE WHEN TRUNC( DateTime ) = TRUNC( SYSDATE ) THEN 1 END )
OVER ( PARTITION BY ReferenceNum ) AS num_today,
COUNT( CASE WHEN TRUNC( DateTime ) <> TRUNC( SYSDATE ) THEN 1 END )
OVER ( PARTITION BY ReferenceNum ) AS num_other_day
FROM table_name t
)
WHERE num_today = 1
AND num_other_day = 0
| REFERENCENUM |
|--------------|
| 789ef |
oracle 中的table 中应该存在两条记录,一条来自请求,一条来自响应。
我想 select 所有今天的记录,但问题是另一对可能存在于前两天或更长时间。 怎么保证返回的记录只有1条,前几天不存在
select A.referenceNum, A.datetime, A.Type from table A where A.datetime >= sysdate - 1
为了形象化,我只想select reference num 789ef.
ReferenceNum DateTime Type
123ab (今天到今天)请求
123ab (日期到今天)响应
456cd (日期到今天)请求
456cd (datetoday-2)响应
789ef (日期到今天)请求
使用NOT EXISTS
运算符
SELECT A.referenceNum, A.datetime, A.Type
from table A
where A.datetime >= sysdate - 1
AND NOT EXISTS (
SELECT null FROM table B
WHERE A.referenceNum = B.referenceNum
AND b.datetime < a.datetime
)
SELECT referenceNum
FROM A A1
WHERE TRUNC(A1.datetime) > TRUNC(sysdate)-1
AND A1.Type = 'Request'
AND NOT EXISTS
(SELECT 1
FROM A
WHERE TRUNC(A.datetime) >= TRUNC(sysdate)-1
AND A.Type = 'Response'
AND A.referenceNum = A1.referenceNum
)
您可以使用分析函数在一次 table 扫描中完成(与使用 NOT EXISTS
相比,后者将使用两次 table 扫描):
SQL Fiddle
Oracle 11g R2 模式设置:
CREATE TABLE table_name ( ReferenceNum, DateTime, Type ) AS
SELECT '123ab', SYSDATE, 'Request' FROM DUAL UNION ALL
SELECT '123ab', SYSDATE, 'Response' FROM DUAL UNION ALL
SELECT '456cd', SYSDATE, 'Request' FROM DUAL UNION ALL
SELECT '456cd', SYSDATE - 2, 'Response' FROM DUAL UNION ALL
SELECT '789ef', SYSDATE, 'Request' FROM DUAL;
查询 1:
SELECT ReferenceNum
FROM (
SELECT ReferenceNum,
COUNT( CASE WHEN TRUNC( DateTime ) = TRUNC( SYSDATE ) THEN 1 END )
OVER ( PARTITION BY ReferenceNum ) AS num_today,
COUNT( CASE WHEN TRUNC( DateTime ) <> TRUNC( SYSDATE ) THEN 1 END )
OVER ( PARTITION BY ReferenceNum ) AS num_other_day
FROM table_name t
)
WHERE num_today = 1
AND num_other_day = 0
| REFERENCENUM |
|--------------|
| 789ef |