簡體   English   中英

Oracle:從列中選擇總和作為兩者:YTD(年初至今)、財政 YTD

[英]Oracle: Selecting Sums From Columns as both: YTD (Year to Date), Fiscal YTD

我對 Oracle 比較陌生,並且一直在嘗試編寫查詢以返回列上的 YTD 和 Fiscal YTD 總計。

只有相關列的表的簡化版本看起來像:

INVOICE_NUM  |  INVOICE_DATE  |  ORDER_CODE  |  ORDER_COST
    509         '14-FEB-20'      'ORD001'         34.99
    509         '14-FEB-20'      'ORD002'         14.99
    509         '14-FEB-20'      'ORD003'         59.99
    428         '16-JAN-20'      'ORD001'         34.99
    428         '16-JAN-20'      'ORD002'         14.99
    306         '14-DEC-19'      'ORD001'         34.99
    306         '14-DEC-19'      'ORD002'         14.99
    201         '15-NOV-19'      'ORD001'         34.99
    108         '16-OCT-19'      'ORD001'         34.99

訂單是根據其他地方的邏輯重新出現在每張發票中的經常性費用。 我需要返回的是給定發票的總成本以及訂單代碼的 YTD 總額以及每個訂單代碼的財政 YTD(從 11 月 1 日開始)。 對於此示例集,我的查詢應返回發票 509:

ORDER_CODE  |  CURRENT_INVOICE_TOTAL  |  YTD_TOTAL  |  FISCAL_YTD_TOTAL
 'ORD001'             34.99                69.69           139.96
 'ORD002'             14.99                29.98            44.97
 'ORD003'             59.99                59.99            59.99

截至目前,我所擁有的是:

SELECT 
    order_code
    SUM(order_cost)
FROM 
    table_name
WHERE 
    invoice_num = :invoice_num
GROUP BY
    order_code

到目前為止,我在 YTD 的嘗試都失敗了,開發環境的數據也很差,所以沒有真正的方法來測試它。 到目前為止,我正計划創建一個帶有假數據的臨時表來嘗試解決這個問題。

為清楚起見編輯:查詢應返回給定發票日期的 YTD 總數。 例如,如果我在 2020 年查詢 2018 年 5 月的發票,它應該返回 2018 年 1 月至 2018 年 5 月該發票中包含的每個 order_code 的 YTD 總計

您可以使用Conditional Aggregation例如

SELECT order_code, 
       SUM(CASE WHEN invoice_num = :invoice_num then order_cost END ) AS current_invoice_total,
       SUM(CASE WHEN to_char(sysdate,'yyyy') = to_char(invoice_date,'yyyy') then
                  order_cost
              END ) AS ytd_total,
       SUM(CASE WHEN invoice_date 
             BETWEEN to_date(to_char(sysdate,'yyyy')-1||'-11-01','yyyy-mm-dd')
                 AND to_date(to_char(sysdate,'yyyy')||'-10-31'  ,'yyyy-mm-dd')
             THEN
                  order_cost
              END ) AS fiscal_ytd_total              
  FROM t
 GROUP BY order_code
 ORDER BY order_code

根據問題中的編輯,在表中使用Cross Join並從:invoice_num綁定變量派生invoice_date :invoice_num

SELECT t.order_code, 
       SUM(CASE WHEN invoice_num = :invoice_num THEN order_cost END ) 
             AS current_invoice_total,
       SUM(CASE WHEN invoice_date 
             BETWEEN TRUNC(invoice_date2,'yyyy')
                 AND invoice_date2
                THEN
                     order_cost
                END ) AS ytd_total,
       SUM(CASE WHEN invoice_date 
             BETWEEN to_date(to_char(invoice_date2,'yyyy')-1||'-11-01','yyyy-mm-dd')
                 AND invoice_date2
                THEN
                     order_cost
                END ) AS fiscal_ytd_total           
  FROM t
 CROSS JOIN ( SELECT MAX(invoice_date) AS invoice_date2 
                FROM t 
               WHERE invoice_num = :invoice_num ) t2
 GROUP BY order_code
 ORDER BY order_code

演示

您可以使用conditional aggregation如下:

Select order_code, 
       order_cost as CURRENT_INVOICE_TOTAL,
       Sum(case when invoice_date >= trunc(sysdate,'YEAR') then order_cost end) as YTD_TOTAL,
       Sum(case when invoice_date < add_months(trunc(sysdate,'YEAR'), 10) order_cost) as FISCAL_YTD_TOTAL
  From table_name
 Where invoice_num = :invoice_num
   And invoice_date >= add_months(trunc(sysdate,'YEAR'), -2)
   And invoice_date < add_months(trunc(sysdate,'YEAR'), 12)
Group by order_code, order_cost

此解決方案將使用invoice_date上的索引(如果有)。

干杯!!

您的財政年度從 11 月開始。 這使得聚合變得非常棘手,尤其是在 10 月11 月都可以使用的版本。

但是,可以通過在日期上加上兩個月並提取年份來計算會計年度。 如果我們采用這種方法,那么一種方法是:

select order_code,
       max(order_cost) keep (dense_rank first order by invoice_date desc) as current_invoice_total,
       sum(case when trunc(invoice_date, 'YEAR') = trunc(sysdate, 'YEAR')
                then order_cost
           end) as YTD,
       sum(case when trunc(invoice_date + interval '2' month, 'YEAR') = trunc(sysdate + interval '2' month, 'YEAR') 
                then order_cost
           end) as Fiscal_YTD
from t
where trunc(invoice_date, 'YEAR') = trunc(sysdate, 'YEAR') or 
      trunc(invoice_date + interval '2' month, 'YEAR') = trunc(sysdate + interval '2' month, 'YEAR')
group by order_code;

是一個 db<>fiddle。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM