• fahey.jonathan (1/20/2012)


    Here is an alternate version using a Tally table.

    Jonathan,

    Nearly but not quite, that just gets next thursday. Not the next first thursday of the month.

    Here's another version loosely based on your Tally table idea.

    I'll try to explain what it does:

    1. Gets all days for this and the next month.

    2. Reduces that set to just Thursdays

    3. Ranks partitioned by month, to number the Thursdays 1 - n

    4. Gets the top Thursday with a rank of 1 that is greater than the target date

    DECLARE @now DATETIME = '20120201'

    SELECT TOP 1

    theDay

    FROM

    (

    SELECT

    theDay,

    --==

    --==Rank the thursdays 1-4 (or possibly 5)

    --==

    theRank = RANK() OVER(PARTITION BY MONTH(theDay) ORDER BY theDay)

    FROM

    (

    --==

    --==Get all the days in this and next month

    --==

    SELECT

    DATEADD(dd,n-1,DATEADD(mm, DATEDIFF(mm,'19000101',@now ) ,'19000101')) theDay

    FROM

    Tally

    WHERE

    N <=

    DATEDIFF(dd,

    DATEADD(mm, DATEDIFF(mm,'19000101',@now) ,'19000101'),

    DATEADD(mm, 2+DATEDIFF(mm,'19000101',@now) ,'19000101'))

    ) alldays

    WHERE

    --==

    --==Get just the Thursdays (note the adjustment for a DATEFIRST setting other than 7)

    --==

    (@@DATEFIRST + DATEPART(dw,theDay)) % 7 = 5

    ) Thursdays

    WHERE

    theRank = 1-- The first thursday

    AND

    theDay > @now-- After the target date

    ORDER BY theDay