
■ 単純な日差
OracleのSQLで差日数を計算してみます。テストデータは、以前に作成した日付一覧(SQL(Oracle)で土日と祝日をそれっぽく考慮した日付一覧の作成)を使います。
2017年8月9日と、日付一覧の抽出結果の差日数を取得するSQLです。
SELECT
TO_DATE(日付, 'YYYYMMDD') AS 日付
,TO_DATE('20170809', 'YYYYMMDD') -
TO_DATE(日付, 'YYYYMMDD') AS 日差
FROM
(
・・・ 前回のサンプルSQLの抽出結果 ・・・
)
ORDER BY 1
注意ですが、上記のSQL文に単純に前の記事のSQLを埋めてもダメです。あれはWITH句をつかっているので、WITH句の部分をSQL文の先頭に移さないと動きません。
取得値を日付型に変換して減算するだけで差日数が取得できます。Oracleは日付型で減算すると差日数になってくれるので楽で良いです。
■ 土日祝日考慮の日差
今度は、もうちょっと複雑に行きます。
開始日が 2017年7月14日(金)。終了日が 2017年7月20日(木)とすると、単純な日差は、6日になります。
ですが、土日祝を考慮すると、2017年7月15日(土)、2017年7月16日(日)、2017年7月17日(月、海の日)の 3日間が抜けるので、差日数は 3日になります。
この結果を取得するSQLはこんな感じです。
SELECT
COUNT(*) - 1 AS 日差
FROM
(
・・・ 前回のサンプルSQLの抽出結果 ・・・
)
WHERE
日付 BETWEEN '20170714' AND '20170720'
ORDER BY 1
日付一覧を指定範囲で抽出して、COUNT関数で件数を取得します。COUNT関数だと同一日が 1 となるので 1 減算します。
■ 複数の日付範囲を指定した日差
上記は日付範囲が1件だけでしたが、複数の日付範囲の場合も作ってみました。日付一覧にぶつけるデータ、DUAL表とUNION ALL を使用して作成しています。
SELECT
A.番号
,A.開始日
,A.終了日
,COUNT(*) - 1 AS 日差
FROM
(
SELECT
1 AS 番号
,TO_DATE('20170714', 'YYYYMMDD') AS 開始日
,TO_DATE('20170720', 'YYYYMMDD') AS 終了日
FROM DUAL
UNION ALL
SELECT
2 AS 番号
,TO_DATE('20170701', 'YYYYMMDD') AS 開始日
,TO_DATE('20170704', 'YYYYMMDD') AS 終了日
FROM DUAL
UNION ALL
SELECT
3 AS 番号
,TO_DATE('20170724', 'YYYYMMDD') AS 開始日
,TO_DATE('20170728', 'YYYYMMDD') AS 終了日
FROM DUAL
) A
,(
・・・ 前回のサンプルSQLの抽出結果 ・・・
) B
WHERE
A.開始日 <= B.日付(+)
AND A.終了日 >= B.日付(+)
GROUP BY
A.番号
,A.開始日
,A.終了日
ORDER BY A.番号
テストデータ(上記の内部テーブルA)の開始日、終了日の範囲で、日付一覧(上記の内部テーブルB)を抽出します。
後は、その単位でCOUNT関数を発行すれば良しです。
最新の記事:http://harikofu.blog.fc2.com/
投稿記事の一覧:http://harikofu.web.fc2.com/
--- blog end ---
スポンサードリンク


