Oracle两行数据相减

突然接到一个需求,所有的数据都在一张大表里,想要找出创建时间间隔大于15分钟的数据。
整体思路为——将创建日期转为秒来计算,but如何进行一张表内两行时间列的差值计算呢
这里就用了Oracle提供的Lag函数。

在这里插入图片描述上图为数据样例,就是上一行减去下一行,以此类推知道最后。
现在使用Lag函数将CreateAt列,平移添加另一列Last_CreateAt,这里不是简单的平移而是把CreateAt的第一行作为了Last_CreateAt的第二行,这样的话,我们将CreateAt-Last_CreateAt就得到了两行之间的差值了

with temp as(
  SELECT 
       CreateAt, 
       LAG(CreateAt) OVER(ORDER BY CreateAt) Last_CreateAt
  FROM table1
  WHERE VIN = 'xxxx' 
  ORDER BY CreateAt
)
select * from temp

下图为使用Lag函数后的样子
在这里插入图片描述接着将日期类型的数值转为秒级使用UNIX_TIMESTAMP函数

with temp as(
  SELECT 
        VIN ,CreateAt, 
        LAG(CreateAt) OVER(ORDER BY CreateAt) Last_CreateAt,
  FROM table1
  WHERE VIN = 'xxxx' 
  ORDER BY CreateAt
),
temp2 as (
  SELECT  VIN ,CreateAt, Last_CreateAt,
  UNIX_TIMESTAMP(CreateAt) as seconds,
  NVL (UNIX_TIMESTAMP(Last_CreateAt),1) as last_seconds
  FROM temp
)
select * from temp2

转换后的结果图
在这里插入图片描述接着就计算差值呗,将大于15分钟的过滤出来

with temp as(
  SELECT 
        VIN ,CreateAt, 
        LAG(CreateAt) OVER(ORDER BY CreateAt) Last_CreateAt
  FROM tabel1
  WHERE VIN = 'xxxx' 
  ORDER BY CreateAt
),
temp2 as (
  SELECT  VIN ,CreateAt, Last_CreateAt,
  UNIX_TIMESTAMP(CreateAt) as seconds,
  NVL (UNIX_TIMESTAMP(Last_CreateAt),1) as last_seconds
  FROM temp
)
SELECT  
        ROW_NUMBER() OVER ( ORDER BY CreateAt ) AS rid,
        temp2.CreateAt,temp2.Last_CreateAt,
        temp2.vin, 
        (temp2.seconds - temp2.last_seconds) as vals
  FROM temp2 
  WHERE temp2.last_seconds is not NULL
  AND (temp2.seconds - temp2.last_seconds) >900

结果图为
在这里插入图片描述那么假设15分钟内的中间有距离,如果想要计算时间大于15分的数据中间的速度,该怎么计算呢。这时需要运用另一个函数Lead——是将数据往上平移。在本次代码中也就是将Last_CreateAt网上平移,与原始的CreateAt中间形成了一个大于15分钟的区间。这样就可以计算距离了。
下面就将整个代码贡献上来了。

with temp as(
SELECT 
      VIN ,CreateAt, LAG(CreateAt) OVER(ORDER BY CreateAt) Last_CreateAt,
      VehTotDistance,
      LAG(VehTotDistance) OVER(ORDER BY CreateAt) last_VehTotDistance
FROM table1
WHERE VIN = 'xxxx' 
ORDER BY CreateAt
),
temp2 as (
SELECT  VIN ,CreateAt, Last_CreateAt,VehTotDistance,last_VehTotDistance,
UNIX_TIMESTAMP(CreateAt) as seconds,
NVL (UNIX_TIMESTAMP(Last_CreateAt),1) as last_seconds
FROM temp
),
temp3 as(
 SELECT  
      ROW_NUMBER() OVER ( ORDER BY CreateAt ) AS rid,
      temp2.CreateAt,temp2.Last_CreateAt,
      lead(Last_CreateAt) Over(ORDER BY CreateAt) new_Last,
      VehTotDistance,last_VehTotDistance,
      lead(last_VehTotDistance) Over(ORDER BY CreateAt) new_last_VehTotDistance,
      temp2.vin, 
      (temp2.seconds - temp2.last_seconds) as vals
FROM temp2 
WHERE temp2.last_seconds is not NULL
AND (temp2.seconds - temp2.last_seconds) >900
)
SELECT  
     temp3.CreateAt beginTime,new_Last endTime,
     NVL(new_last_VehTotDistance - VehTotDistance,0) Distance,
     NVL((new_last_VehTotDistance - VehTotDistance)/3600,0) V
FROM   temp3

最终的结果为

在这里插入图片描述The End Thanks

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值