2013-06-27 129 views
2

我需要連續unpayments量:排名在連續日期

with payments as 
(
select '1' as ID, '20130331' as DateR, 'Not_paid' as Status from dual 
union 
select '1' as ID, '20130430' as DateR, 'Paid' as Status from dual 
union 
select '1' as ID, '20130531' as DateR, 'Not_paid' as Status from dual 
union 
select '2' as ID, '20130331' as DateR, 'Not_paid' as Status from dual 
union 
select '2' as ID, '20130430' as DateR, 'Not_paid' as Status from dual 
union 
select '3' as ID, '20130331' as DateR, 'Paid' as Status from dual 
union 
select '3' as ID, '20130430' as DateR, 'Paid' as Status from dual 
union 
select '3' as ID, '20130531' as DateR, 'Paid' as Status from dual 
) 

select ID, dater, status, dense_rank() over (partition by ID, status order by dater asc) rnk from payments 

當你從這個我從ID 2 unpayments正確數量的看到:他的第一個unpayment是在三月,第二在四月份。 Id 3也沒問題,因爲我稍後會排除他,但對於id 1,它表示第二次未付款是在五月份,而我想將它作爲第一個,因爲他在三月份沒有付款,但在四月再次付款它應該從那裏開始排名。一旦他支付了最後一筆款項,這個過程就會重新開始

這個想法是保持簡單而沒有複雜的查詢。我只需要做同樣的密度排名,但只有當日期是連續的

我希望這個例子足夠清楚。

編輯: 這是我從當前查詢得到:

ID DATER  STATUS RNK 
1 20130331 Not_paid 1 
1 20130531 Not_paid 2 
1 20130430 Paid  1 
2 20130331 Not_paid 1 
2 20130430 Not_paid 2 
3 20130331 Paid  1 
3 20130430 Paid  2 
3 20130531 Paid  3 

而我希望得到的是這樣的:

ID DATER  STATUS RNK 
1 20130331 Not_paid 1 
1 20130430 Paid  1 
1 20130531 Not_Paid 1 
2 20130331 Not_paid 1 
2 20130430 Not_paid 2 
3 20130331 Paid  1 
3 20130430 Paid  2 
3 20130531 Paid  3 

這樣的,如果我想獲得最大(等級)來檢查用戶當前有多少未付款,我得到該ID有1個未付款,ID 2兩個連續未付款,ID 3有0個未付款。這是因爲在連續第四次付款時,我必須將用戶視爲攪動。

編輯:29/06/2013

有人給了我在另一個論壇的完美解決方案: https://forums.oracle.com/thread/2555552

+0

你能展示你的預期產出嗎?您可以使用'LAG'來檢查以前的狀態,這有助於確定連續的值。 –

+1

嗨,編輯我的帖子,使其更清楚我所期待的。我已經嘗試了LAG,但是我必須通過一張有800萬行的表格來查詢它,並且處理需要很長的時間,而密集的排名只需要幾秒鐘,並且非常容易進一步處理結果。 – vdBurg

回答

0

這不是一個完整的回答你的問題,但它是一個可能的解決方案,以獲得每個ID的未付款數目。它爲Not_paid狀態分配值1,爲付費狀態分配-1值。因此,我們可以通過ID對查詢進行分組,並對值列進行求和以獲取未付款項的數量。對於負數的款項,我們將其分配爲零,因爲它們沒有未付款。

with payments as 
(
select '1' as ID, '20130331' as DateR, 'Not_paid' as Status from dual 
union 
select '1' as ID, '20130430' as DateR, 'Paid' as Status from dual 
union 
select '1' as ID, '20130531' as DateR, 'Not_paid' as Status from dual 
union 
select '2' as ID, '20130331' as DateR, 'Not_paid' as Status from dual 
union 
select '2' as ID, '20130430' as DateR, 'Not_paid' as Status from dual 
union 
select '3' as ID, '20130331' as DateR, 'Paid' as Status from dual 
union 
select '3' as ID, '20130430' as DateR, 'Paid' as Status from dual 
union 
select '3' as ID, '20130531' as DateR, 'Paid' as Status from dual 
) 
SELECT id, 
     DECODE(SIGN(SUM(value)), -1, 0, SUM(value)) 
    FROM (SELECT id, 
       dater, 
       status, 
       DECODE(status, 'Paid', -1, 1) value 
      FROM payments 
     ) 
GROUP BY id 
ORDER BY id; 

現在,此查詢適用於您的示例中的數據集,但可能無法用於更大的數據集。如果Not_paid狀態的付費狀態數量不少,也不會有效。例如,在您的ID = 2的示例中,如果帳戶在5月份全額支付,則需要將2付費條目加載到您的表中才能使我的解決方案發揮作用。如果只加載了1個付費條目,那麼我的解決方案仍然會顯示此ID所需的未付款項。

+0

謝謝!這可能是一個部分解決方案,但是我在Oracle論壇上得到了一個完美的答案。如果其他人感興趣,我已經通過鏈接編輯了評論 – vdBurg