我希望将一些独特的逻辑放入查询中,而不必调用函数。
在这个应用程序中,我正在查看给定股票代码的最后4个报告季度。表中的日期表示为YYYYMM,如下例所示:
201804,
201801,
201710,
201704
现在,可能会有四分之一的缺失。也许该公司没有提交季度报告,或其他什么。
所以,我想要做的是看是否存在缺口或缺少季度:
201804,
201710,
201704,
201701
在这里,201801缺失........我想我必须能够比较MONTHS_BETWEEN当前记录日期,LEAD 1或NTH_VALUE 1日期值,并看到差异为3几个月.......最后4个记录(4个季度)。如果没有,则缺少某些记录,并且我将返回NULL值,这是应用程序所需的值。
任何想法或独特的逻辑?或者我需要编写一个函数代码,然后调用它?
感谢!!!
答案 0 :(得分:0)
只需将所有内容转换为日期,并使用自连接日期操作
<强> SQL Fiddle 强>
i32
<强>输出强>
With cte as (
SELECT "val",
TO_DATE("val", 'YYYYMM') as original
FROM Table1
)
SELECT c1."val", c1.original,
c2.original as next_quarter,
c3.original as previous_quarter
FROM cte c1
LEFT JOIN cte c2
ON c1.original = ADD_MONTHS(c2.original, -3)
LEFT JOIN cte c3
ON c1.original = ADD_MONTHS(c3.original, 3)
ORDER BY c1."val"
答案 1 :(得分:0)
您可以使用季度数据创建季度和外部日历的日历。这是查询的外观。 var arr = [0,20,40,60,80];
arr.forEach((element, index) => {
arr[index] = index + 1;
});
console.log(arr); // [1, 2, 3, 4, 5]
是您的日历开始的年份,p_start_year
计算日历中显示的季度数。
p_no_of_qtrs
结果就是这样。
WITH
mydata
AS
(SELECT '201804' AS quarter FROM DUAL
UNION
SELECT '201801' AS quarter FROM DUAL
UNION
SELECT '201710' AS quarter FROM DUAL
UNION
SELECT '201704' AS quarter FROM DUAL),
calendar
AS
(SELECT TO_CHAR (
ADD_MONTHS (
TO_DATE (:p_start_year || '-01-01', 'YYYY-MM-DD'),
(LEVEL
- 1)
* 3
),
'YYYYMM'
)
AS quarter
FROM DUAL
CONNECT BY LEVEL <= :p_no_of_qtrs)
SELECT c.quarter, d.quarter AS status
FROM mydata d,
calendar c
WHERE c.quarter = d.quarter(+)
ORDER BY c.quarter;
缺少的季度显示为NULL。