blog.toxn

あしあと

T-SQLでカレンダーを作る

日付をキーとするようなデータを1ヶ月分表示するようなときに使える。 レコードが毎日作られるとは限らない場合、テーブルに保存されているデータだけではどこが欠けているのか分からないが、これを使えば全日分並べることができる。

declare @d as date = '2017-01-01';

with _month(i) as ( select 0 as i union all select i+1 from _month where i < datediff(day, @d, EOMONTH(@d)))
select * from (select cast(DateAdd(day, i, @d) as date) as 日付 from _month) as A

何をしているのか

変数でその月の初日を用意しておく

そのまんま。

declare @d as date = '2017-01-01';

再帰CTE(共通テーブル式)を使って、その月の日数を列挙していく

そのテーブル式にwith句で_monthと名前をつけた。 EOMONTH関数を使うとその月の末日を返してくれるので、datediff関数で1日から末日までの日数差を出す。 結果、1月ならば列iに0〜30の値が入ったテーブル_monthができる。

with _month(i) as ( select 0 as i union all select i+1 from _month where i < datediff(day, @d, EOMONTH(@d)))

用意した変数に、DateAdd関数で日数を足していく

intervalをdayにして、0〜その月の日数-1 を足していけばカレンダーの出来上がり。

select * from (select cast(DateAdd(day, i, @d) as date) as 日付 from _month) as A

あとは、別のテーブルの日付とjoinすれば完了です。