Populate a field with the next Monday in April - sql

I need to create a new field in my select query which selects the Next first Monday of April if the date is greater than '2003-03-31' is that possible.
For example i have a date 2014-04-21 so I need the calculated date to return as 2015-04-6.
Second example would be 2020-01-13 so the calculated date would need to return 2020-04-6
UPDATED
Data is below:
What I have been attempting is:
CASE
WHEN Date <= '2003-03-31' THEN
'2004-04-5'
WHEN Date > '2003-03-31' THEN
????? (First Monday of the next April)
END AS 'Test1',
This is where I m stuck sorry I was so vague.

As I believe that you have written a small mistake in your question :
Second example would be 2020-01-13 so the calculated date would need
to return 2010-04-6
You wanted to write :
Second example would be 2020-01-13 so the calculated date would need
to return 2020-04-6
Here is how you can do it:
SELECT Date_c
, case when Date_c >= DATEADD(DAY, (9 - DATEPART(dw,CONVERT(date,concat(year(Date_c), '-04-01')))), CONVERT(date,concat(year(Date_c), '-04-01')))
then DATEADD(DAY, (9 - DATEPART(dw,CONVERT(date,concat(year(Date_c)+1, '-04-01')))), CONVERT(date,concat(year(Date_c)+1, '-04-01')))
else DATEADD(DAY, (9 - DATEPART(dw,CONVERT(date,concat(year(Date_c), '-04-01')))), CONVERT(date,concat(year(Date_c), '-04-01')))
end as NEXTMONDAY
from testT
where Date_c > '2003-03-31';
Here is the DEMO

Related

Find number of days in a given week according to the month for a given date. in SQL

Consider the date "2022-07-02"
For the month July first week only have 3 days in it.
I need to find the number of days in the week for the given date.
In above date the week has 3 days where "2022-07-02" day reside.
Example 2 :
For month June in 2022 first week has 5 days in the week
Therefore if i declare a date as "2022-06-03" it should pass the number of days in the week as 5
I need a query to find the number of days for the specific week.
set datefirst 1 -- assumes Monday is set as start of week
declare #myDate date = getdate();
-- calculate the next last day of week
declare #nextSunday date = dateadd(day, 7 - datepart(weekday, #myDate), #myDate);
select case
-- advancing into the next month implies a partial week
-- datediff(month, #myDate, nextSunday) = 1 would be equivalent
when day(#nextSunday) < day(#myDate) then 7 - day(#nextSunday)
-- else see if still within first week
when day(#nextSunday) < 7 then day(#nextSunday)
else 7 end;
Within a query you might use it this way:
select case
when day(nextSunday) < day(dateColumn) then 7 - day(nextSunday)
when day(nextSunday) < 7 then day(nextSunday)
else 7 end
from
myData cross apply (
values (dateadd(day, 7 - datepart(weekday, dateColumn), dateColumn))
) v(nextSunday);
https://dbfiddle.uk/?rdbms=sqlserver_2019&fiddle=ee5bfb52dabe31dd619cfd136689db59
If you don't want the shorthand form then just replace every instance of nextSunday in the final step with its full expression.
There's nothing in the logic that prevents this from working with another first day of week. I just chose a variable name that helped ellucidate this particular problem.

Select records when month and day are less than current date

I am using SQL Server Mgmt Studio. I need to create a formula that will only select records when the month and day of a date/time field, LAW_TAEEMASTER.MASTR_ENTRY, is less than or equal to the current month and day. For example, If LAW_TAEEMASTER.MASTR_ENTRY = 8/20/2015 and current date = 7/6/2017, exclude. If LAW_TAEEMASTER.MASTR_ENTRY = 12/21/2014 and current date = 1/15/2017, include. Date formatting is my weakness. Here is what I have tried:
select LAW_TAEEMASTER.MASTR_ENTRY
from LAW_TAEEMASTER
WHERE day(LAW_TAEEMASTER.MASTR_ENTRY) <= DAY(GETDATE()) and MONTH(LAW_TAEEMASTER.MASTR_ENTRY) <= MONTH(getdate())
and
select LAW_TAEEMASTER.MASTR_ENTRY
from LAW_TAEEMASTER
WHERE AND DATEPART(DAY,LAW_TAEEMASTER.MASTR_ENTRY) <= DATEPART(DAY,GETDATE()) AND DATEPART(MONTH,LAW_TAEEMASTER.MASTR_ENTRY) <= DATEPART(MONTH,GETDATE())
but these just evaluate the month and day separately and as a number, greater than or less than, so it's excluding records. How can I get SQL to recognize these as part of a date and just ignore the year?
I would do this using month() and day():
where month(LAW_TAEEMASTER.MASTR_ENTRY) * 100 + day(LAW_TAEEMASTER.MASTR_ENTRY) < month(getdate()) * 100 + day(getdate())
If performance is an issue, I would recommend a computed column with an index.
Explain the logic and code:
Use CONVERT(varchar(5),<your_date> ,110)). The 110 arguement means USA standard time and have an ouput like mm-dd-yyyy. Then we only take the first five character which is the month and day of the date.
110 = mm-dd-yyyy
read more about cast and convert here
my sample table:
MASTER_ENTRY
2017-08-30
2017-07-05
2017-07-04
Then I executed this query
SELECT LAW_TAEEMASTER.MASTR_ENTRY
FROM LAW_TAEEMASTER
WHERE CONVERT(varchar(5),LAW_TAEEMASTER.MASTR_ENTRY ,110) <= CONVERT(varchar(5),GETDATE() ,110)
result:where month and day equal or earlier current month and day
MASTER_ENTRY
2017-07-05
2017-07-04
I hope this helps and welcome to StackOverflow. If you find this answer or any other answer solves your problem please mark it as the solution. This will help the community and fellow programmers who run into the same problem in the future. Thanks.

Get Year of Previous Month (For Jan 1st)

I'm currently building a YTD report in SSRS. I'm looking to edit the default "FROM" date in a calendar selection.
I'm looking to retrieve January 1st of the previous months year. For example:
(If it's Feb 16th, 2016 .. the result should be 1/1/2016
If it's Jan 10th, 2016 .. the result should be 1/1/2015)
I built this to retrieve the current year for jan 1st, but it causes issues if we're in January because I need it to retrieve the year of the previous month (in that case it would be 2015, not 2016).
Thanks!
Try this, it should work
=DateAdd(DateInterval.Month,-1,DateSerial(Year(Today), Month(Today), 1))
UPDATE:
Based on your comment I've created this expression. It is not tested but should work.
=IIF(Today.Month>1,
DateAdd(DateInterval.Month,-1,DateSerial(Year(Today), Month(Today), 1)),
DateAdd(DateInterval.Year,-1,DateSerial(Year(Today), Month(Today), 1))
)
Let me know if this helps.
select cast(cast(year(dateadd(mm, -1,getdate())) as varchar)+'-01-01' as date)
replace getdate() with which ever field you're basing this calculation on.
for testing:
select cast(cast(year(dateadd(mm, -1,'2015-01-22')) as varchar)+'-01-01' as date)
select cast(cast(year(dateadd(mm, -1,'2016-02-01')) as varchar)+'-01-01' as date)
select cast(cast(year(dateadd(mm, -1,'2015-12-12')) as varchar)+'-01-01' as date)
We want to use Date Serial which has the forma
=DateSerial(YYYY,MM,DD)
The Month is always January
The day is always the first
If the month is January, it's last year. Otherwise, it's this year.
So, assuming we have an SSRS report with a parameter called Date , we can create a new field for your January date as follows:
=iif(Month(Parameters!Date.Value)=1,
dateserial(Year(Parameters!Date.Value)-1,1,1),
dateserial(Year(Parameters!Date.Value),1,1))
if you want to do this in the query with T-SQL (version 2012) or later:
case when month(#DATE) = 1
then DATEFROMPARTS(YEAR(#DATE)-1,1,1)
else DATEFROMPARTS(YEAR(#DATE),1,1)
end
OR, in earlier versions
CASE WHEN MONTH(#DATE) = 1
THEN CAST(CAST((YEAR(#DATE)-1)*10000 + 101 AS CHAR(8)) AS DATE)
ELSE CAST(CAST((YEAR(#DATE)*10000+ 101) AS CHAR(8)) AS DATE)
END

How to get every Monday out of a Date

I need some help to understand a certain line in a code. The code takes the turnovers of every Monday in the year 2010 and at the last line in summarizes all the turnovers to one.
Here is the code:
SELECT
CASE
WHEN GROUPING (DATUM) = 1 THEN 'Gesamtumsatz'
ELSE CAST (DATUM AS VARCHAR (40))
END AS MONTAGSDATEN,
AVG (VERKAUFSWERT * VERKAUFSMENGE) as UMSATZ
FROM Data_Star_Awesome.dbo.VERKAUFSFAKTEN vk
INNER JOIN DIMDATUM dimD on vk.DATUMID=dimD.DATUMID
WHERE DATEDIFF(dd,0, DATUM)%7=0
AND JAHR = 2010
GROUP BY ROLLUP (DATUM)
The problematic line I don't understand is the following:
WHERE DATEDIFF(dd,0, DATUM)%7=0
What I know is that it takes the days out of the date variable but I don't get the %7=0 part. The DATEDIFF function should give back all the days. Are these days saved in the % the placeholder? And how does it get all the Mondays by using the 7=0?
It would be great if someone could help me out.
Thanks a lot :)
Modulo or % operator is the same as in a lot of programming languages. It returns the remainder after the division.
The DATEDIFF function takes two dates and returns the difference in a specified datepart, which in your query is the days represented by dd.
Also 0 as date converts to 1/1/1900 which happens to be a Monday. So your query is calculating the days between 1/1/1900 and the DATUM field in days and if its Mod is 0 then DATUM is Monday.
You could simply say:
datename(weekday,<datetime-value>)
Which will return 'Monday', 'Tuesday', 'Wednesday', etc. The problem with this approach is that the returned value is localized. If the SQL server's language is changed, your test for 'Monday' will fail.
This expression will always work:
( ##datefirst + ( datepart(weekday,today) - 1 ) ) % 7
It evaluates to 1-7, where Monday is always 1 and Sunday is always 7, regardless of culture/language settings or the current value of ##datefirst, as set by set datefirst.
We can then convert this into this discriminant function, yielding 1 or 0 to indicate whether or not the date is Monday:
case ( ##datefirst + ( datepart(weekday,today) - 1 ) ) % 7 when 1 then 1 else 0 end

Get 1st Day of Week (Sunday)

I have this formula in my column to calculate the start date of a given week :
dateadd(week,[Week]-(1),
dateadd(day,(-1),
dateadd(week,
datediff(week,(0),
CONVERT([varchar](4),[Year],(0))+'-01-01'),
(1))))
Where Week and Year are other fields like 38 and 2012
Problem is, it calculates the start date of week 38/2012 as a monday (17th Sept), I would like it to be a sunday instead (16th Sept) is this possible?
Many thanks.
This will return you the first day of the week, given a week number and a year, assuming that the first day of the week is a Sunday.
Standard exclusions apply, e.g. don't try year 1499.
declare #tbl table ([Week] int, [Year] int)
insert #tbl select 38,2012
union all select 1,2012
union all select 0,2012
union all select 1,2013
select DATEADD(
Week,
[Week]-1,
DATEADD(
Day,
(8-##datefirst)-DATEPART(dw, CAST([Year]*10000+101 AS VARCHAR(8))),
CAST([Year]*10000+101 AS VARCHAR(8))))
from #TBL
Result
2012-09-16 00:00:00.000
2012-01-01 00:00:00.000
2011-12-25 00:00:00.000
2012-12-30 00:00:00.000
Note that the Week number starts from 1, and if the week doesn't start on a Sunday, then the first day of that week could end up in an earlier year (row #4). Because the Weeks are relative, you can use Week 0, -1 etc and it will still give you a result (row #3), rightly or wrongly.
You may also notice I used a different method to create a date out of the year, just as an alternative.
The (8-##datefirst) portion of the query makes it robust regardless of your DATEFIRST setting.
If you want the first day of the week to be Sunday you could change your database to make it so, using the DATEFIRST setting.
function getFirstDateOfThisWeek(d)
{
var TempDate = new Date(d || new Date());
TempDate.setDate(TempDate.getDate() + (#Config.WeekStartOn - 1 - TempDate.getDay() - 7) % 7);
return TempDate;
}
var StartDate = getFirstDateOfThisWeek(new Date()); //1st date of this week