2016-09-26 8 views
1

時間を時間範囲と比較したいと思います。その時間範囲がその時間範囲にある場合は、レコードを返す必要があります。例えばSql Server - 24時間形式でのみ時間を比較しますか?

、テーブル「A」があります2016-09-26 02:51:59

+-----------+------+-------------+-----------+ 
| User_Code | Name | Shift_Start | Shift_End | 
+-----------+------+-------------+-----------+ 
|   1 | ABC | 04:01:00 | 11:00:00 | 
|   2 | DEF | 11:01:00 | 20:00:00 | 
|   3 | XYZ | 20:01:00 | 04:00:00 | 
+-----------+------+-------------+-----------+ 

を今、私は、そのシフトそれは、この特定の日時にあったを確認したいです。 SQLクエリはUser_Code = 3を返します。 Shift_StartおよびShift_Endは、タイプtimeである。

私は時間に2016-09-26 02:51:59を変換してからbetweenを使用してshift_startshift_endと比較してlogical operatorを使用して試してみましたが、私は望ましい結果を得ることができません。

これは私を困惑させました。私は解決策を見出そうとしてから1時間が経過していますが、私はそうすることができません。試してグーグルが、そこにも何も得ていない。どんな助けもありがとう。他の角度からのSQL Server 2012

+1

をお試しください:00:00〜04:00:00:00〜04:00:00:00:00:00:00〜00:00:23:59:59 XYZ' – paul

+0

@paul、はい、私は本当にDBの構造を変更したいとは思わないが、これは事をもっと簡単にすることに同意する。 – NewbieProgrammer

答えて

3

シフト時間は、いずれの順序でもよいので、あなたは、より複雑なwhere条件を必要としています。

ので:

where ((shift_start < shift_end) and 
     cast(@datetime as time) between shift_start and shift_end) 
    ) or 
     ((shift_start > shift_end) and 
     cast(@datetime as time) not between shift_end and shift_start) 
    ) 
+0

兄さんありがとう。私は「間」ではないことも理解できませんでした。 – NewbieProgrammer

+0

@Gordon Linoff、私はこれが答えられていることを知っています。 @datetime = '2016-09-24 17:51:59'を渡そうとすると、代わりに2行(2&3)が与えられます。 – user3583912

+0

@ user3583912 。 。 'between'と 'not between'の演算子は、最初に低い値を持つ必要があります。 –

0

アプローチを使用し、シフトの開始時刻と終了時刻に検索条件の日付部分を追加します:case文を

注意、これは変速終了が深夜に交差するような状況を処理します。

DECLARE @dateTime DATETIME = '2016-09-26 02:51:59' 
-- Remove the time portion of above 
DECLARE @datePortion DATETIME = DATEADD(dd, 0, DATEDIFF(dd, 0, @dateTime)) 

SELECT * FROM TableA 
    WHERE @dateTime BETWEEN @datePortion + cast(Shift_Start as datetime) 
        AND CASE WHEN ShiftEnd < ShiftStart 
          THEN DATEADD(day, 1, @datePortion) 
          ELSE @datePortion 
         END + cast(Shift_End as datetime) 
+0

残念ながら、これは望ましい結果をもたらしませんでした。 – NewbieProgrammer

1
declare @t table(
    User_Code int, 
    Name varchar(20), 
    Shift_Start time, 
    Shift_End time 
    ); 
insert @t(User_Code,Name,Shift_Start,Shift_End) 
values 
(1,'ABC','04:01:00','11:00:00') 
,(2,'DEF','11:01:00','20:00:00') 
,(3,'XYZ','20:01:00','04:00:00'); 

あなただけ `TIME`なく` DATETIME`に対処したい場合、それはあなたの `20を分割するためにあなたの人生を容易にするかもしれない

declare @d datetime = '2016-09-26 02:51:59'; 

select * 
from @t 
cross apply (-- intermediate vars: rounded param 
     select dt = cast(cast(@d as date) as datetime) 
      ) r 
where @d between dateadd(d, case when Shift_Start<Shift_End then 0 else -1 end, dt) + cast(Shift_start as datetime) 
     and dt+cast(Shift_end as datetime); 
関連する問題