簡體   English   中英

我可以使用Oracle SQL從計划信息中繪制實際日期嗎?

[英]Can I use Oracle SQL to plot actual dates from Schedule Information?

我問了有關SQL Server的問題 ,但是Oracle環境(10g)的答案是什么?

如果我有一個表,其中包含表示特定日期的計划信息,是否可以編寫一條SQL語句,以使用MSSQL的“ Commom表表達式”之類的信息將該信息轉換為實際的行?

考慮帶有以下列的付款時間表表:

  • StartDate-計划開始的日期(第一筆付款應於該日期支付)
  • 期限 -計划的月份長度
  • 頻率 -兩次重復之間的月數
  • PaymentAmt-付款金額:-)
SchedID  StartDate    Term  Frequency  PaymentAmt
-------------------------------------------------
1        05-Jan-2003  48    12         1000.00 
2        20-Dec-2008  42    6          25.00

是否有一條SQL語句可以讓我從上面轉到下面?

Running
SchedID Payment  Due          Expected
        Num      Date         Total
--------------------------------------
1       1        05-Jan-2003  1000.00
1       2        05-Jan-2004  2000.00
1       3        05-Jan-2005  3000.00
1       4        05-Jan-2006  4000.00
2       1        20-Dec-2008  25.00
2       2        20-Jun-2009  50.00
2       3        20-Dec-2009  75.00
2       4        20-Jun-2010  100.00
2       5        20-Dec-2010  125.00
2       6        20-Jun-2011  150.00
2       7        20-Dec-2011  175.00

您的想法受到贊賞。

Oracle實際上具有使用CONNECT BY子句進行分層查詢的語法。 相比之下,SQL Server對WITH子句的使用看起來像是hack:

    SELECT t.SchedId,
           CASE LEVEL
             WHEN 1 THEN
               t.StartDate
             ELSE
               ADD_MONTHS(t.StartDate, t.frequency)
             END 'DueDate',
           CASE LEVEL
             WHEN 1 THEN
               t.PaymentAmt
             ELSE
               SUM(t.paymentAmt)
           END 'RunningExpectedTotal'
      FROM PaymentScheduleTable t
     WHERE t.PaymentNum <= t.Term / t.Frequency
CONNECT BY PRIOR t.startdate = t.startdate
  GROUP BY t.schedid, t.startdate, t.frequency, t.paymentamt
  ORDER BY t.SchedId, t.PaymentNum

我不是100%的人-我對使用以下內容更有信心:

    SELECT t.SchedId,
           t.StartDate 'DueDate',
           t.PaymentAmt 'RunningExpectedTotal'
      FROM PaymentScheduleTable t
     WHERE t.PaymentNum <= t.Term / t.Frequency
CONNECT BY PRIOR t.startdate = t.startdate
  ORDER BY t.SchedId, t.PaymentNum

...但是它不包含處理鏈中第二個以上條目以增加月份和總和的邏輯。 可以使用GROUP BY CUBE或ROLLUP進行求和,具體取決於所需的細節。

我不明白為什么schedid = 1需要5個付款日,scheid = 2需要7個付款日?

48/12 = 4和42/6 =7。因此,我預計schedid = 1需支付4天。

無論如何,我使用模型子句:

create table PaymentScheduleTable 
( schedid   number(10)
, startdate date
, term      number(3)
, frequency number(3)
, paymentamt number(5)
);

insert into PaymentScheduleTable 
values (1,to_date('05-01-2003','dd-mm-yyyy')
, 48
, 12
, 1000);

insert into PaymentScheduleTable 
values (2,to_date('20-12-2008','dd-mm-yyyy')
, 42
, 6
, 25);

commit;

現在選擇帶模型子句:

select schedid, to_char(duedate,'dd-mm-yyyy') duedate, expected, i paymentnum
from   paymentscheduletable
model  
partition by (schedid)
dimension by (1 i)
measures (
  startdate duedate
, paymentamt expected
, term 
, frequency) 
rules 
( expected[for i from 1 to term[1]/frequency[1] increment 1] 
  = nvl(expected[cv()-1],0) + expected[1]
, duedate[for i from 1 to term[1]/frequency[1] increment 1] 
  = add_months(duedate[1], (cv(i)-1) * frequency[1])
)
order by schedid,i;

輸出:

   SCHEDID DUEDATE      EXPECTED PAYMENTNUM
---------- ---------- ---------- ----------
         1 05-01-2003       1000          1
         1 05-01-2004       2000          2
         1 05-01-2005       3000          3
         1 05-01-2006       4000          4
         2 20-12-2008         25          1
         2 20-06-2009         50          2
         2 20-12-2009         75          3
         2 20-06-2010        100          4
         2 20-12-2010        125          5
         2 20-06-2011        150          6
         2 20-12-2011        175          7


11 rows selected.

我沒有打算回答自己的問題,但是我現在正在與Oracle一起工作,我不得不學習一些新的Oracle風格的東西。

無論如何,CONNECT BY語句確實非常好-是的,比MSSQL的層次查詢方法好得多,並且使用該構造,我能夠生成一個非常干凈的查詢,該查詢可以滿足我的要求:

SELECT DISTINCT
     t.SchedID
    ,level as PaymentNum
    ,add_months(T.StartDate,level - 1) as DueDate
    ,(level * t.PaymentAmt) as RunningTotal
FROM SchedTest t
CONNECT BY level <= (t.Term / t.Frequency)
ORDER BY t.SchedID, level

我唯一剩下的問題是我必須使用DISTINCT,因為我無法弄清楚如何從DUAL(和aff的單行Oracle表)中選擇行,而不是從計划數據表中選擇行,該表至少有兩行。 如果可以使用FROM DUAL進行上述操作,則不需要DISTINCT指示器。 有什么想法嗎?

除此之外,我認為這還不錯。 嗯?

暫無
暫無

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

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