2014-05-08 164 views
0

尋找使用SQL 2008 R2的查詢的幫助...我有一個包含客戶端和日期字段的表。大多數客戶對大多數日期都有記錄,但有些則沒有。 例如,我有這樣的數據:查詢返回缺少日期範圍的第一個日期

CLIENTID  DT 
1   5/1/14 
1   5/2/14 
2   5/3/14 
3   5/1/14 
3   5/2/14 

我可以通過創建期間所有可能的日期的temp table,然後加入,爲每個CLIENTIDDT只有選擇那裏是找到每個CLIENTID缺少的日期一個NULL

這是我能得到輕鬆的日期範圍14年5月1日至14年5月4日:

CLIENTID  DTMISSED 
1   5/3/14 
1   5/4/14 
2   5/1/14 
2   5/2/14 
2   5/4/14 
3   5/3/14 
3   5/4/14 

但是我想每個組連續錯過必合,並得到各的開始期限和長度。

例如,如果我使用日期範圍14年5月1日至14年5月4日我想獲得:

CLIENTID  DTSTART MISSED 
1   5/3/14  2 
2   5/1/14  2 
2   5/4/14  1 
3   5/3/14  2 

感謝您的幫助!

+0

嗯爲什麼你在最後一個例子中有'3','5/1/14','1'?我認爲在這個例子中它應該被滑雪? – Darka

+0

太對了!我固定了表格 - 謝謝你的發現... – Trees

+0

正如我現在所看到的,你可以一個接一個地去更新額外的列,這將用於分組(不是很好的選擇,但不能想到更好的東西) – Darka

回答

1

這是令人着迷的是如何更優雅,也僅僅是有效的這樣那樣的問題,可以在2012年

一,表解決:

create table #t (CLIENTID int, DT date) 
go 
insert #t values 
(1,   '5/1/14'), 
(1,   '5/2/14'), 
(2,   '5/3/14'), 
(3,   '5/1/14'), 
(3,   '5/2/14') 
go 

create table #calendar (dt date) 
go 
insert #calendar values ('5/1/14'),('5/2/14'),('5/3/14'),('5/4/14') 
go 

這裏的2008解決方案:

;with x as (
    select *, row_number() over(order by clientid, dt) as rn 
    from #calendar c 
    cross join (select distinct clientid from #t) x 
    where not exists (select * from #t where c.dt=#t.dt and x.clientid=#t.clientid) 
), 
y as (
    select x1.*, x2.dt as x2_dt, x2.clientid as x2_clientid 
    from x x1 
    left join x x2 on x1.clientid=x2.clientid and x1.dt=dateadd(day,1,x2.dt) 
), 
z as (
    select *, (select sum(case when x2_dt is null then 1 else 0 end) from y y2 where y2.rn<=y.rn) as grp 
    from y 
) 
select clientid, min(dt), count(*) 
from z 
group by clientid, grp 
order by clientid 

將其與2012年比較:

;with x as (
    select *, row_number() over(order by dt) as rn 
    from #calendar c 
    cross join (select distinct clientid from #t) x 
    where not exists (select * from #t where c.dt=#t.dt and x.clientid=#t.clientid) 
), 
y as (
    select x1.*, sum(case when x2.dt is null then 1 else 0 end) over(order by x1.clientid,x1.dt) as grp 
    from x x1 
    left join x x2 on x1.clientid=x2.clientid and x1.dt=dateadd(day,1,x2.dt) 
) 
select clientid, min(dt), count(*) 
from y 
group by clientid, grp 
order by clientid 
+0

哇Dean是一些忍者的東西! – Trees

+0

除了我需要它顯示一些客戶誰沒有任何記錄在#噸,基本上顯示爲錯過4開始5/1 ...我想我必須加強'x'。 – Trees

+0

正確。在x CTE中加入一些日期,以創建矩陣。哪些客戶與哪些日期,你做選擇:) – dean