T SQL Первый вторник в диапазоне дат - PullRequest
0 голосов
/ 05 апреля 2019

Используя SQL Server, мне нужно проработать 1-й вторник между датой начала цикла и датой окончания периода.Однако мой код возвращает неправильную дату.

Это мой код:

SELECT 
    CONVERT(DATETIME, CONVERT(VARCHAR(10), [BUCKET_START])) AS  Bucket_Start,
    CONVERT(DATETIME, CONVERT(VARCHAR(10), [BUCKET_END])) AS Bucket_End,
    DATEADD(dd, - 6, DATEADD(wk, DATEDIFF(wk, 0, dateadd(dd, 7 - DATEPART(day, CONVERT(DATETIME, CONVERT(VARCHAR(10), [BUCKET_START]))),   
    CONVERT(DATETIME, CONVERT(VARCHAR(10), [BUCKET_END])))), 0)) AS [1st_Tuesday]
FROM 
    [BUCKETS]
WHERE 
    CAT_CODE = 1013
    AND BUCKET_START < CONVERT(NVARCHAR, GETDATE(), 112)
    AND BUCKET_END > CONVERT(NVARCHAR, GETDATE(), 112)

И вот текущие результаты:

Bucket_Start      Bucket_End      1st_Tuesday
2019-03-31        2019-04-27      2019-03-26

Однако правильный 1-й вторник:

Bucket_Start      Bucket_End      1st_Tuesday
2019-03-31        2019-04-27      2019-04-02

Почему мой запрос все еще просматривается в марте?

Спасибо за любую помощь.

Ответы [ 4 ]

0 голосов
/ 11 июля 2019

Это не совсем то, что вы просите, но я уверен, что вы можете использовать его, чтобы получить требуемые результаты.

DECLARE  @Day INT = 3;
 --Sunday    1
 --Monday    2
 --Tuesday   3
 --Wednesday 4
 --Thurday   5
 --Friday    6
 --Saturday  7 
 DECLARE  @StartDate DATETIME = GETDATE();

 SELECT  DATEADD(DD, @Day - DATEPART(WEEKDAY, @StartDate) + IIF(@Day - DATEPART(WEEKDAY, @StartDate) >= 0, 0, 7), @StartDate)

Измените> = на>, если хотите, чтобы следующий не включал сегодня

0 голосов
/ 05 апреля 2019

мы можем достичь этого с помощью оператора case.

    SELECT 
CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])) AS Bucket_Start,
CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_END])) AS Bucket_End,
case when     abs((select  DATEparT(weekday  ,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))))) in  (1,2,3)
                  then    DATEadd(weekday,  3 -  abs((select  DATEparT(weekday  ,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))))), CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
                  else   DATEadd(weekday,  3 + ( 7 - abs((select  DATEparT(weekday  ,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))))), CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))  
                  end AS [1st_Tuesday]
FROM [BUCKETS]
WHERE   BUCKET_START < CONVERT(NVARCHAR, GETDATE(), 112)
AND BUCKET_END > CONVERT(NVARCHAR, GETDATE(), 112)
0 голосов
/ 05 апреля 2019

Спасибо всем за помощь!Я пошел со следующим:

SELECT
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) as Bucket_Start_Day, 
CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])) AS Bucket_Start,
CASE
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Sunday' then 
DATEADD(DD,2,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Monday' then 
DATEADD(DD,1,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Tuesday' then 
CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Wednesday' then 
DATEADD(DD,6,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Thursday' then 
DATEADD(DD,5,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Friday' then 
DATEADD(DD,4,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
WHEN
DATENAME(dw,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START]))) = 'Saturday' then 
DATEADD(DD,4,CONVERT(DATETIME, convert(VARCHAR(10), [BUCKET_START])))
END AS '1st_Tuesday'
FROM [BUCKETS]
WHERE CAT_CODE = 1013
AND BUCKET_START < CONVERT(NVARCHAR, GETDATE(), 112)
AND BUCKET_END > CONVERT(NVARCHAR, GETDATE(), 112)

Это дает мне следующее:

Bucket_Start_Day    Bucket_Start               1st_Tuesday
Sunday          2019-03-31 00:00:00.000    2019-04-02 00:00:00.000
0 голосов
/ 05 апреля 2019

Добавьте 6 дней к началу, если это среда, 5, если это четверг, ..., 0, если это вторник.

SELECT Bucket_Start, DATEADD(DAY, CASE DATENAME(WEEKDAY, Bucket_Start_Date)
    WHEN 'Wednesday' THEN 6
    WHEN 'Thursday'  THEN 5
    WHEN 'Friday'    THEN 4
    WHEN 'Saturday'  THEN 3
    WHEN 'Sunday'    THEN 2
    WHEN 'Monday'    THEN 1
    WHEN 'Tuesday'   THEN 0
END, Bucket_Start_Date) AS First_Tuesday
FROM Buckets
CROSS APPLY (
    -- convert int 20190301 to date
    SELECT CAST(CAST(Bucket_Start AS VARCHAR(8)) AS DATE) AS Bucket_Start_Date
) AS CA
...