Automating a holiday date for any year in Matlab - matlab

The code below gives a decimal day for one specific year.
HolidayArrayDate(2) = datenum(2012,01,16,00,00,00); %MartinLutherKingJrBirthday
I am trying to make the holiday more general for an input "dataYear" instead of specifying it as "2012". Martin Luther King Jr Birthday is the third Monday of ever year. When i provide it an input of any year 2010/2011/2012/2013/2014 through "dataYear", it should automatically choose the third Monday in January for me. How would i dot this?
Thank you!

Starting from the first day of the year, 21 days always suffice to find the third Monday. So: get serial date number for first day of the year (with datenum); get day-of-the-week for that and the following 20 days (datestr(..., 'd')); find the first three Mondays (find(...=='M', 3); and finally pick the third one and convert it into date string (datestr):
dataYear = 2012; %// input
f = datenum(dataYear,1,1); %// 1st day of year, in serial date number format
r = find(datestr(f+(0:20), 'd')=='M', 3); %// find three Mondays from that day on
result = datestr(f+r(3)-1); %// third Monday, in date string format

Related

how to simulate date for one year in kdb

i would like to simulate random timestamp data.
100 records in a day for one year.
How am I am able to do that?
when i set a:2013.01.01D00:00:00.000000000
100?a
the randomize data doesn't stay in a day.
thanks for your input
I am not sure, if this can be done easily. But you may generate 100 random timestamps for every day of 2013 in the next way
daysInYear: 365;
year: 2013.01.01D00:00:00.000000000;
//array of 365 elements, where every element represents corresponding date of year
dates: year + 01D * til daysInYear;
//array of 365 elements, where every element is an array of 100 random timestamps [0 .. 1D)
randomNanos: cut[100; (100 * daysInYear)?1D];
//array of 365 elements, where each element is an array of 100 random dateTimes for given day
result: dates + randomNanos;
//put all the dates in single array
raze result
The short version which does the same is below:
raze (2013.01.01D+01D * til 365) + cut[100; (100*365)?1D]
In order to simulate data for a single day, it's possible to generate random times (as floats less than one) and add them to the day you would like to generate data for. In this case:
D:2016.03.01;
D+100?1f
Will return 100 random times on 2016.03.01. If you want to generate data within a time range you can restrict the size of the float to something less than 1, or greater than a certain minimum value.
If you want to handle leap years... Not sure of a better way at the minute other than adding the max number of days onto the start of the year and asking whether it's the 31st. Adding on 366, it can either be 31st or 1st. If it's the 31st good, otherwise drop off the last date.
/e.g.
q)last 2015.01.01+til 365
2015.12.31
q)last 2016.01.01+til 365
2016.12.30 /we are a day short
q)
/return the dates and the number of days based on whether its a leap year
q)dd:$[31i~`dd$last d:2016.01.01+til 366;(366;d);(365;-1_d)]
q)/returns (366;2016.01.01 2016.01.02...)
q)/the actual logic below is pretty much the same as the other answer
q)raze{[n;dy;dt] dt+n cut(n*dy)?.z.N}[100;].dd
2016.01.01D16:06:53.957527121 2016.01.01D10:55:10.892935198 2016.01.01D15:36:..

datenum series to the end of February - Leap year or not

I want to create a list of dates that go until the end of February. However, since the end of February changes from 28 to 29 depending on whether there's a leap year, I'm having trouble with how to consider both options.
Here's what I have so far:
date = datenum(years(i),12,01):1:datenum(years(i)+1,02,29);
This case, when run on a year that is not a leap year, ends up counting March 1st instead of ending on Feb. 28th.
Here's a little hack I came up with. You can check whether a year is a leap year quite easily by calculating the number of days between February 28 and March 1, like so:
datenum(years(i), 3, 1) - datenum(years(i), 2, 28)
Checking whether it's larger than 1 would indicate leap year. This 1 or 0 logical MATLAB convention leads to the second part of the hack: this is exactly the number of days you need to add to Feb 28: 0 if not leap year, 1 if leap year. Here, therefore, is the full hack:
date = datenum(years(i),12,01):datenum(years(i)+1,02, ...
28 + ((datenum(years(i)+1,3,1) - datenum(years(i)+1,2,28))>1) );
UPDATE / IMPROVEMENT:
Answer already accepted, but I came up with an even better solution. I didn't realize that datenum simply counts days. In this case, we can simply say that the last day of February is the day before March 1. This yields the following drastic simplification:
date = datenum(years(i),12,01):1:(datenum(years(i)+1,3,1)-1);
Datenum, for good or ill, takes negative and zero numbers. So the last day of February can be written:
datenum(2015, 3, 0)
With a comment explaining this madness, of course.

Access datediff using calculated first day of the year

I'm creating a new form in Access 2010. I need to create a field that will calculate a year to date timeframe, in months, using a calculated value for the first day of the year. The scenario is that the user will input a date. Then, Access will calculate a value for months YTD, based on the date the user keys. The catch is that the user may input a date for the current year, or a date from a previous year. So, I cannot simply hard code a baseline date, like 1/1/2014, to perform the calculation. I need Access to generate the first day of the year, based on the date entered, then perform the calculation.
Example: User enters '4/10/2013'
Access calculates months YTD from '1/1/2013' to '4/10/2013'.
Expected Result: 3.25 Months
I need this to assist with calculating income, which will utilize dates over multiple years.
I quickly created this function for you:
Public Function calcmonths(datecalc As Date) As Double
calcmonths = Round(DateDiff("d", DateSerial(Year(datecalc), 1, 1), datecalc) * 12 / DateDiff("d", DateSerial(Year(datecalc), 1, 1), DateSerial(Year(datecalc) + 1, 1, 1)), 2)
End Function
You can use it with the input from your form. It calculates the first day of the entered year with DateSerial(Year(datecalc), 1, 1) , then calculates the difference in days. That result is multiplied by 12 (months) and divided by the number of days within that year (calculated to make sure leap years are 366 days). In the end the result is rounded to 2 decimal numbers.

How to check whether it is a Saturday and Sunday respectively in MATLAB

I would like to check whether it is Saturday and Sunday in MATLAB. I know there is a function called busday in MATLAB to check whether it is a business day but I would like to check whether it is Saturdays or Sunday respectively so that I find the corresponding Monday, which I need in my calculation.
Need some guidance on how to do this.
You need the weekday function:
http://www.mathworks.com/help/matlab/ref/weekday.html
D = '21-Dec-2012';
[DayNumber,DayName] = weekday(D)
DayNumber =
6
DayName =
Fri

Concatenate variable horizontally to make one variable in matlab

Is it possible to concatenate multiple variable horizontally to make a single variable in Matlab?
For Example, I want to join:
year = 2001, month = 06, day = 15
to make one variable '20010615' which I could search in a matrix.
I hope I am clear.
Regards,
If you want a string output, use string formatting and sprintf
sprintf('%04d%02d%02d', year, month, day );
If you want a numeric output, simply multiply
day + 100 * month + 10000 * year
Update:
Thanks to #Joshua's comment: if you are indeed working with date/time information you should also look into datestr that allows more speciallized formatting for date and time information.