我在 Oracle 数据库中有一个事务表。我正在尝试为涉及多种交易类型的交付系统整理一份报告。 “请求”类型实际上可以是四种子类型之一(本例中为“A”、“B”、“C”和“D”),而“交付”类型可以是四种不同子类型之一。类型(“拉”、“取”、“邮件”)。从“请求”到“交付”,可以有 1 到 5 个交易来获取物品,并且许多“交付”类型也是中间交易。示例:
Item | Transaction | Timestamp
001 | REQ-A | 2014-07-31T09:51:32Z
002 | REQ-B | 2014-07-31T09:55:53Z
003 | REQ-C | 2014-07-31T10:01:15Z
004 | REQ-D | 2014-07-31T10:02:29Z
005 | REQ-A | 2014-07-31T10:05:47Z
002 | PULL | 2014-07-31T10:20:04Z
002 | MAIL | 2014-07-31T10:20:06Z
001 | PULL | 2014-07-31T10:22:21Z
001 | TRANSFER | 2014-07-31T10:22:23Z
003 | PULL | 2014-07-31T10:24:10Z
003 | TRANSFER | 2014-07-31T10:24:12Z
004 | PULL | 2014-07-31T10:26:28Z
005 | PULL | 2014-07-31T10:28:42Z
005 | TRANSFER | 2014-07-31T10:28:44Z
001 | ARRIVE | 2014-07-31T11:45:01Z
001 | PICKUP | 2014-07-31T11:45:02Z
003 | ARRIVE | 2014-07-31T11:47:44Z
003 | PICKUP | 2014-07-31T11:47:45Z
005 | ARRIVE | 2014-07-31T11:49:45Z
005 | PICKUP | 2014-07-31T11:49:46Z
我需要的是这样的报告:
Item | Start Tx | End Tx | Time
001 | REQ-A | PICKUP | 1:53:30
002 | REQ-B | MAIL | 0:24:13
003 | REQ-C | PICKUP | 1:46:30
004 | REQ-D | PULL | 0:23:59
005 | REQ-A | PICKUP | 1:43:59
我拥有的:
Item | Start Tx | End Tx | Time
001 | REQ-A | PULL | 0:30:49
001 | REQ-A | TRANSFER | 0:30:51
001 | REQ-A | ARRIVE | 1:53:29
001 | REQ-A | PICKUP | 1:53:30
002 | REQ-B | PULL | 0:24:11
002 | REQ-B | MAIL | 0:24:13
003 | REQ-C | PULL | 0:22:55
003 | REQ-C | TRANSFER | 0:22:57
003 | REQ-C | ARRIVE | 1:46:29
003 | REQ-C | PICKUP | 1:46:30
004 | REQ-D | PULL | 0:23:59
005 | REQ-A | PULL | 0:22:55
005 | REQ-A | TRANSFER | 0:22:57
005 | REQ-A | ARRIVE | 1:43:58
005 | REQ-A | PICKUP | 1:43:59
我正在做什么来获取这些数据:
SELECT Item, Transaction, nextTransaction, nextTimestamp - Timestamp
FROM (
SELECT Item, Transaction, Timestamp,
LEAD(Transaction, 5) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTransaction"
LEAD(Timestamp, 5) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTimestamp"
FROM Transactions
UNION ALL
SELECT Item, Transaction, Timestamp,
LEAD(Transaction, 4) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTransaction"
LEAD(Timestamp, 4) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTimestamp"
FROM Transactions
UNION ALL
SELECT Item, Transaction, Timestamp,
LEAD(Transaction, 3) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTransaction"
LEAD(Timestamp, 3) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTimestamp"
FROM Transactions
UNION ALL
SELECT Item, Transaction, Timestamp,
LEAD(Transaction, 2) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTransaction"
LEAD(Timestamp, 2) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTimestamp"
FROM Transactions
UNION ALL
SELECT Item, Transaction, Timestamp,
LEAD(Transaction, 1) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTransaction"
LEAD(Timestamp, 1) OVER (PARTITION BY Item ORDER BY Timestamp) AS "nextTimestamp"
FROM Transactions
)
WHERE nextTransaction IS NOT NULL
AND Transaction IN ('REQ-A', 'REQ-B', 'REQ-C', 'REQ-D')
我可以在脚本中手动解析它(也许这实际上是最好的操作过程),但为了学习,我想知道是否可以仅使用 SQL 来实际完成此操作。