2015-09-15 3 views
1

ExplainationПользовательского диапазон дат

Есть 2 рабочих смены, дневная смена = от 07:00:00 до 19:00:00 и ночной смены = от 19:00:00 к 07:00:00


SAMPLE DATA

Name Date  Time  WorkShift 
John 2015-09-14 19:14:24 N 
John 2015-09-14 23:43:27 N 
John 2015-09-15 03:21:36 N 
John 2015-09-15 11:29:48 D 

DESIRED РЕЗУЛЬТАТ

К примеру у меня @dateStart = 2015-09-14 и @dateEnd = 2015-09-14 переменные. Мне нужно, чтобы выбрать записи из 2015-09-14 19:00:00 в 2015-09-15 07:00:00 в следующем:

John 2015-09-14 19:14:24 N 
John 2015-09-14 23:43:27 N 
John 2015-09-15 03:21:36 N 

Как вы видите выше, здесь дата 2015-09-15, но Time является 03:21:36 поэтому она должна быть выбрана (потому что время ниже, чем 07:00:00, N рабочей смены).


ПРОБЛЕМЫ

Мой запрос выбора, как и ожидалось, но есть 2 проблемы.

Если я прохожу @dateStart = 2015-09-15 и @dateEnd = 2015-09-15 Это выбор:

John 2015-09-15 03:21:36 N -- this shouldn't be selected again, this should go as 2015-09-14 
John 2015-09-15 11:29:48 D 

Другая проблема заключается в том, что если у меня есть запись, как этот

John 2015-09-15 03:21:36 N 

Как вы видите, нет никаких записей для John в 2015-09-14 так Его следует выбирать, когда я передаю переменные в следующем: @dateStart = 2015-09-15 и @dateEnd = 2015-09-15


QUERY

select * 
from SampleTable 
where /* Some conditions.... and*/ 
     (convert(date, StartTime) >= @dateStart) and 
     (case when (DateCreated between cast(cast(cast(DateCreated as date) as varchar(40)) + ' 19:00:00' as datetime) 
           and cast(cast(cast(DateCreated as date) as varchar(40)) + ' 23:59:59' as datetime) 
        or 
        DateCreated between cast(cast(cast(DateCreated as date) as varchar(40)) + ' 00:00:00' as datetime) 
           and cast(cast(cast(DateCreated as date) as varchar(40)) + ' 07:00:00' as datetime) 
       ) 
        and Workshift like '%N' 
      then dateadd(day,-1,cast(cast(DateCreated as date) as varchar(40))) 
      else DateCreated 
     end <= @dateEnd) 

Если что-то непонятно - спрашивайте меня, и я попытаюсь объяснить.

+0

один раз, когда я столкнулся с аналогичной проблемой в моей программе регистрации посещаемости, мне пришлось использовать временную метку вместе с AM/PM и проверить ее, чтобы решить проблему.Я думаю, это может помочь тебе. Почему ты не проверяешь это. –

+0

Любая конкретная причина не принимать значение datetime в типе данных DATE и вместо этого хранить его как varchar? –

+0

@RahulTripathi нет, нет никаких конкретных причин, просто не было идей, как сделать это по-другому. –

ответ

1

попробовать это один

select * 
from SampleTable 
where convert(dateTime,DateCreated) + convert(dateTime,StartTime) 
between DATEADD(HH,7, @dateStart) and DATEADD(HH,24+7, @dateEnd) 
or 
(
    convert(dateTime,DateCreated) + convert(dateTime,StartTime) 
    between DATEADD(HH,00, @dateStart) and DATEADD(HH,7, @dateStart) -- Morning records 
    and not exists 
     (
     select 1 from SampleTable where 
     convert(dateTime,DateCreated) + convert(dateTime,StartTime) 
     between DATEADD(HH,7-24, @dateStart) and DATEADD(HH,0, @dateStart) 
     ) -- Data from previous day 
) 
+0

Благодарим вас за ответ, но он кажется неправильным. Он возвращает тот же результат в течение 14 дней и тот же результат в течение 15 дней (как в примере) –

+0

Получил его. Для каждого дня вам нужна только дневная смена и ночь ... И вам нужно выбрать строки для утренних записей, если нет данных за предыдущий день. Обновленное решение –

+0

Спасибо, похоже, работает после некоторых исправлений. –

2

Как насчет добавления часов в начале и в конце?

where datetime >= dateadd(hour, 19, @datestart) and 
     datetime < dateadd(hour, 7, @dateend) 

При хранении «дата» и «время» в отдельных колонках (который обычно не рекомендуется), вы можете добавить их после преобразования в datetime:

where cast(date as datetime) + cast(time as datetime) >= dateadd(hour, 19, @datestart) and 
     cast(date as datetime) + cast(time as datetime) < dateadd(hour, 7, @dateend) 
Смежные вопросы