Database JUNKY

MySQL,MariaDBを中心としたブログです

MySQL日付の範囲内でのレコード重複チェックをSQLで実現する

日付(From - To )にて、レコードが重複(かぶっている)ものを抽出するSQLのサンプルです。うーん、なんて言えばいいのか

日付期間の重複チェック と言えばいいのか、日時の範囲チェックというべきか・・・なかなか難易度が高かったので、メモを残しておきます

f:id:hit10231023:20180309103851j:plain

テーブル定義

desc t1 ;
+--------------+---------------------+------+-----+-------------------+-----------------------------+
| Field        | Type                | Null | Key | Default           | Extra                       |
+--------------+---------------------+------+-----+-------------------+-----------------------------+
| Id           | bigint(20) unsigned | NO   | PRI | NULL              |                             |
| StartAt      | datetime(3)         | NO   |     | NULL              |                             |
| EndAt        | datetime(3)         | NO   |     | NULL              |                             |
+--------------+---------------------+------+-----+-------------------+-----------------------------+

t1 テーブルの概要

  • idは、プライマリーキー
  • startAt は開始日時
  • endAtは、終了日時

このstartAt、endAtが範囲内でかぶってはいけないというルールで、重複しているものを抽出するSQLは以下のような感じになると思います。あ、MySQLでのサンプルです

SQL

こんな感じなるのかな? t1 というテーブルを、v1 , v2 と別名で作成して、チェックをかけております

SELECT 
  v1.id,
  v2.id AS dup_id,
  v1.startAt AS v1start,
  v1.EndAt AS v1end,
  v2.startAt AS v2start,
  v1.EndAt AS v2end
FROM
  v4.t1 v1, 
  v4.t2 v2
WHERE 
(
(v1.StartAt >= v2.StartAt AND v1.StartAt <= v2.EndAt) OR 
(v1.EndAt >= v2.StartAt AND v1.EndAt <= v2.EndAt)
)   
AND v1.Id != v2.Id
ORDER BY 
  v1.Id,v2.Id
;

上記SQLの結果

こんな感じものがでてきました。

v1.StartAt - v1.EndAt v2.StartAt - v2.EndAt

でデータが範囲内で重複しているのがわかるかと思います

*************************** 1. row ***************************
          id: 968549391649058
      dup_id: 245249464892456
     v1start: 2018-01-09 21:04:23.850
       v1end: 2018-01-09 21:43:05.500
     v2start: 2018-01-09 21:03:46.580
       v2end: 2018-01-09 21:43:05.500
*************************** 2. row ***************************
          id: 968549391649058
      dup_id: 832274483203399
     v1start: 2018-01-09 21:04:23.850
       v1end: 2018-01-09 21:43:05.500
     v2start: 2018-01-09 21:40:50.350
       v2end: 2018-01-09 21:43:05.500

。とまあ。これだけなんですけど汗