MATLAB Answers

0

Daily 3d array to monthly- dealing with alternate days in a month and leap years - How to do it?

Asked by Behzad Navidi on 26 Oct 2019
Latest activity Commented on by Behzad Navidi on 26 Oct 2019
I have a 720x360x365 matrix (let's call it A) of daily precipitation for one year. 365 stands for days in a year. I need to write a code to convert these daily data to the monthly sum. If I start from January, I need to do mean (A,3) of the first 31 days, then the mean (A,3) of February, the next 28 or 29 days. Because the days alternate between 31 and 30 (and 28 or 29 for February), I don't know how to write a code to do this.
please help me I don't know how to do it.
thank you

  0 Comments

Sign in to comment.

1 Answer

Answer by Rik
on 26 Oct 2019
 Accepted Answer

You don't have another option than just hardcoding the number of days in a month. You can do this in a fancy way using the date functions in Matlab, or just look at a calender. The fact that you have 365 days means that you are dealing with a non-leap year, so February only has 28 days.
There are probably simpler ways to solve it, but you can easily convert this 3D matrix to a cell array, apply the function you already suggested to each cell and then convert back to a 3D matrix.
A=rand(720,360,365);%generate example array
month_lengths=[31 28 31 30 31 30 31 31 30 31 30 31];%non-leap year
B=mat2cell(A,size(A,1),size(A,2),month_lengths);%divide into 1 cell per month
B=cellfun(@(x) mean(x,3),B,'UniformOutput',false);%find mean for each month
B=cell2mat(B);%convert back to 3D array

  6 Comments

I'm not in a spot where I can fully investigate this right now, but I'm confident that if you know the date of your first entry, you could use the datetime function and the month function to convert the integers 1:365 or 1:366 into numeric month values, and split based on that.
So you have a separate 3D array for each year? And you need a monthly average separate for each year? In the latter case it would be trivial to use something like this:
if size(A,3)==365
month_lengths=[31 28 31 30 31 30 31 31 30 31 30 31];%non-leap year
else
month_lengths=[31 29 31 30 31 30 31 31 30 31 30 31];%leap year
end

Sign in to comment.