我正在尝试显示每个费率以及开始和结束日期的笼子数量。这将进入发票,我们每天为每个笼子开具账单,这些笼子可以有不同的费率。
这不是一个简单GROUP BY
的获取MIN
和MAX
日期,因为笼子的数量可以下降或上升,然后再次回到相同的数字,所以我只需要查看连续数据。
我搜索了一个解决方案并找到了这个答案。我对其进行了一些修改以满足我的需要并提出了这个:
WITH cte(rate_name, cages, use_date) AS (
SELECT 'I1', 8, DATE'2017-11-04' FROM DUAL UNION ALL
SELECT 'I1', 8, DATE'2017-11-05' FROM DUAL UNION ALL
SELECT 'I1', 7, DATE'2017-11-07' FROM DUAL UNION ALL
SELECT 'I1', 7, DATE'2017-11-10' FROM DUAL UNION ALL
SELECT 'I1', 7, DATE'2017-11-11' FROM DUAL UNION ALL
SELECT 'I1', 8, DATE'2017-11-12' FROM DUAL UNION ALL
SELECT 'I1', 8, DATE'2017-11-13' FROM DUAL UNION ALL
SELECT 'I1', 8, DATE'2017-11-14' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-01' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-02' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-03' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-04' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-05' FROM DUAL UNION ALL
SELECT 'I1 - BR', 1, DATE'2017-11-06' FROM DUAL UNION ALL
SELECT 'I1 - BR', 1, DATE'2017-11-07' FROM DUAL UNION ALL
SELECT 'I1 - BR', 1, DATE'2017-11-08' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-09' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-10' FROM DUAL UNION ALL
SELECT 'I1 - BR', 5, DATE'2017-11-11' FROM DUAL
)
SELECT
a.rate_name,
a.cages,
MIN(a.use_date) AS startdate,
MAX(a.use_date) AS enddate
FROM (
SELECT
cte.use_date,
cte.rate_name,
cte.cages,
ROW_NUMBER() OVER (ORDER BY cte.rate_name, cte.use_date) - ROW_NUMBER() OVER (PARTITION BY cte.rate_name, cte.cages ORDER BY cte.use_date) AS grp
FROM cte
) a
GROUP BY a.rate_name, a.cages, a.grp
ORDER BY a.rate_name ASC, 3;
我在 PL/SQL 中运行了这个查询,它似乎非常适合我想要做的事情。当我尝试在我们正在使用的软件工具中插入解决方案时,结果发现它不支持ROW_NUMBER()
、OVER
和PARTITION BY
.
有没有一种方法可以在不必使用这些内置功能的情况下获得相同的结果?
我已经开始考虑ROW_NUMBER()
手动实施并找到了这种方法。当我测试它时它似乎有效,但我并没有真正插入它。我现在有点坚持实施PARTITION BY
,我只是觉得有点失落,不知道我是否朝着正确的方向前进。
编辑
我刚刚注意到查询返回了不正确的结果。
对于I1
带有7
笼子的情况,应该返回 2 行。第一行开始并结束于2017-11-07
,而第二行开始于2017-11-10
并结束于2017-11-11
。