仅当Oracle中状态列中的状态更改时,才选择一行或多行

时间:2014-03-18 07:22:39

标签: sql oracle

我在Oracle Table(CarStatus)中有一个样本数据,日期范围为01mar14到31mar14:

CarID | CarModel | Date    | StatusCode | Duration
100   | Toyota   | 01Mar14 | Ready      | 24
100   | Toyota   | 02Mar14 | Ready      | 24
100   | Toyota   | 03Mar14 | Ready      | 12
100   | Toyota   | 03Mar14 | Workshop   | 03
100   | Toyota   | 03Mar14 | Inspection | 09
100   | Toyota   | 04Mar14 | Inspection | 04
100   | Toyota   | 04Mar14 | Ready      | 20
100   | Toyota   | 05Mar14 | Ready      | 24
............
100   | Toyota   | 31Mar14 | Ready      | 24
200   | Honda    | 01Mar14 | Workshop   | 24
200   | Honda    | 02Mar14 | Workshop   | 24
200   | Honda    | 03Mar14 | Workshop   | 10
200   | Honda    | 03Mar14 | Inspection | 14
200   | Honda    | 04Mar14 | Inspection | 04
200   | Honda    | 04Mar14 | Ready      | 20
200   | Honda    | 05Mar14 | Ready      | 24
200   | Honda    | 06Mar14 | Ready      | 24
200   | Honda    | 07Mar14 | Ready      | 24
...................
200   | Honda    | 31Mar14 | Ready      | 24

我希望结果只选取值已更改的行。输出应为:

CarID | CarModel | Date    | StatusCode | Duration
100   | Toyota   | 01Mar14 | Ready      | 24   
100   | Toyota   | 03Mar14 | Ready      | 12
100   | Toyota   | 03Mar14 | Workshop   | 03
100   | Toyota   | 03Mar14 | Inspection | 09
100   | Toyota   | 04Mar14 | Inspection | 04
100   | Toyota   | 04Mar14 | Ready      | 20
100   | Toyota   | 05Mar14 | Ready      | 24
200   | Honda    | 01Mar14 | Workshop   | 24   
200   | Honda    | 03Mar14 | Workshop   | 10
200   | Honda    | 03Mar14 | Inspection | 14
200   | Honda    | 04Mar14 | Inspection | 04
200   | Honda    | 04Mar14 | Ready      | 20
200   | Honda    | 05Mar14 | Ready      | 24

有人可以帮我查询吗?或者逻辑只能拿起上述条件记录?上面的持续时间列是小时/天....此表维护每天每小时的carID状态

提前致谢

2 个答案:

答案 0 :(得分:0)

在查询中使用DISTINCT仅保留唯一结果。 DISTINCT关键字可用于仅返回不同(不同)的值。

http://www.w3schools.com/sql/sql_distinct.asp

答案 1 :(得分:0)

您正在寻找LAG功能,您可以使用该功能查看上一条记录中的数据。不幸的是,它不能在where子句中使用,因此你需要一个内部和外部选择。

select carid, carmodel, statusdate, statuscode, duration
from
(
  select carstatus.*, lag(duration) over (order by carid, statusdate) AS previous_duration
  from carstatus
)
where duration <> nvl(previous_duration,-1)
order by carid, statusdate;

我重命名了您的日期状态日期,因为日期是保留字。

(顺便说一句:carmodel真的是carstatus表中的一列吗?对于每个carid来说都是一样的,所以它应该在汽车表中而不是在状态表中。)