Using Trapz on datetime

Hi, I have this graph with the Power value on the y-axis and the datetime on the x-axis (overall a week is shown). I want to caluculate various areas below the curves and plot these. Up to now, I have used the "fill" function to do so, but in the last graph I need to calculate the area beneath one curve dependent on the area beneath another of the curves.
I don't know how to create that dependency with fill, or how to actually evaluate the integral that the fill function shows.
Now I saw that I could use the trapz function to calculate the integral, but somehow that does not plot a graph when I use it. I do not get an error message, but I don't get a plot either. What can I do?
I have also tried to convert the datetime values to datenum, I thought that might be the problem, but that does not work either!

9 Comments

dpb
dpb on 11 Dec 2021
trapz isn't a plotting routine at all -- it just calculates the area/integral of the waveform it is provided Also NB: from the documentation
"trapz reduces the size of the dimension it operates on to 1, and returns only the final integration value. cumtrapz also returns the intermediate integration values, preserving the size of the dimension it operates on"
Also, trapz/cumtrapz don't support datetime. You'll want to convert your x data to numeric:
xForInt = x - x(1); % duration
xForInt = hours(xForInt); % double representing hours
cumtrapz(xForInt,y)
dpb
dpb on 13 Dec 2021
"... trapz/cumtrapz don't support datetime." @Eric Sofen
Would seem a useful/reasonable enhancement request???
Yes. I've created an enhancement request for it for us to reason on. The OP needs datetimes as the ordinate values. There are some conceptual issues to be worked out if the values being integrated are datetimes, but that's probably much less common.
dpb
dpb on 13 Dec 2021
"some conceptual issues to be worked out if the values being integrated are datetimes, ..."
Indeed -- I'm not sure what that would be, either, otomh.
I'd think there would be very few issues raised if were to simply restrict it to the integrating variable and not even bother to try to support the other.
@Eric Sofen your solution does something, but I don't understand at all what.
Can you first of all elaborate on your first two lines of code? I don't understand what they do exaclty, because when I look at my xForInt, thats just the numbers one to 120. Thats not what needs to happen, the last value of y has to still be multiplied by one (each timevalue is at a distance of an hour to each other).
Can you also explain why you use cumtrapz?
And most importantly, how do I plot this back into the graph, with the duration on the x-axis?
Is there maybe a way to just use the area funciton to bypass all of this? The reason I did not do this in the first place is that at the end I still need values for the areas beneath the curves of every day (each peak happens on a day, so my curve is showing five days in case that wasn't clear). I need the seperate values for each day, I don't just need the integral of the curve. That's also a difficulty, because I don't get where I can define that in the trapz function.
Sorry for this messy question!
dpb
dpb on 15 Dec 2021
" I need to calculate the area beneath one curve dependent on the area beneath another of the curves."
But you've given us no klew at all upon what that dependence is...nor did you attach your data (use paperclip and a .mat file or attach the input file that contains the data) to make it simpler for somebody to try to solve your problem once you do get it defined.
@Eric Sofen converted the datetime variable to a duration by the expedient of subtracting the first time value -- that leaves the elapsed time from the beginning of the trace. The second line simply does return the values of the duration as a double that cumtrapz can integrate over as the ordinate since it has not been updated to handle durations nor datetimes The reason to use cumtrapz is the one I outlined earlier -- it returns the value of the cumulative integral at the input points that is a usable variable for plotting.
However, lacking the definition of just what/how this is to be done, precisely, to satisfy your wishes/needs, the above will be the integral over the entire time trace, not over subset regions within it. To do that, you'll have to define the start and stop times inside the overall time trace and iterate over those intervals to accumulate the integrals individually -- or subtract the total of the overall integral up to the wanted start time for each -- either would amount to the same thing.
You'll need to build a grouping variable by day or whatever section of the day is desired and use it to select the subsections...there are tools built into the timetable object or use findgroups and splitapply or perhaps even groupsummary with a user function could be adapted...
Okay so I attached a file where all the relevant info is of what I want to do exactly, and here an explanation:
I need to create three plots that are supposed to simulate a battery loading. As you can see in the picture of my question, my y-values are power values and my x-values are datetime values. The plot is supposed to show the battery load and unload throughout 5 days.
The first subplot is supposed to display when loading happens, which is the area underneath the red curve, but only for certain conditions. I have written the conditions, but have used fill to plot this. That is problematic, because fill obviously doesnt give me the value of this area, and I need the value for calculations later on.
The second is the unloading process, basically it has the same conditions in reverse.
The third is supposed to be both the loading and unloading process combined. The battery is only supposed to load up until a certain capacity and unload only with the loaded capacity (the capacity is power*time, which is also why I thought of using trapz or area).
Basically my problem is the third subplot, as I need the plot to display the right thing with a datetime x-axis and also still need values for the capacity, or integral of each day.
Can you give me advice on how to best solve this?
%info:
%dt = datetime of five days in one hour steps
%PV_Leistung = red curve (120 datapoints)
%Power3 = blue curve (120*4 datapoints)
%AL.Leistung_Gesamt = green curve (120 datapoints)
%Loading Process
q1 = PV_Leistung - Power3(1:4:end) - AL.Leistung_Gesamt; %loading with the power value for the time when red curve is over the blue and green one
w1 = (PV_Leistung - Power3(1:4:end)>0) | (PV_Leistung - AL.Leistung_Gesamt>0); %vector of ones where these two conditions are true (loading)
idx = find(w1); %index of these values
y1 = zeros(120,1); %vector of zeros is created
y1(idx) = q1(w1); %vector is filled with PV Values for the spots where condition w is true = loading, as long as red curve is over blue &green
y1(y1>600) = 600; %maximum power of loading possible is 600 kW
y1(y1<0) = 0; %specifies that only positive y-values are plotted
%Unloading Process
q2 =Power3(1:4:end) + AL.Leistung_Gesamt - PV_Leistung; %unloading with the power value for the time when red curve is beneath the blue and green one
w2 = (Power3(1:4:end) - PV_Leistung>0) | (AL.Leistung_Gesamt-PV_Leistung>0); %vector of ones where these two conditions are true (unloading)
idx = find(w2); %indicies of these values
y2 = zeros(120,1); %vector of zeros is created
y2(idx) = q2(w2); %vector is filled with PV Values for the spots where condition w is true = loading, as long as red curve is beneath blue &green
y2(y2>750) = 750; %maximum power of unloading is 750 kW
y2(y2<0) = 0; %specifies that only positive y-values are plotted
%plots
figure(2)%loading curve
subplot(3,1,1)
b1 = fill(dt,(y1),'r');
ylim([-100 1000]);
title("Ladeprozess")
subplot(3,1,2)
b2 = fill(dt,(y2),'r');
ylim([-100 1000]);
title("Entladeprozess")
%load only until 3040 kWh is reached
%unload only with capacity that has been loaded before
subplot(3,1,3)
area(dt,l)
ylim([-100 1000]);
title("Ausleung")
dpb
dpb on 15 Dec 2021
I'm extremely pressed for time at the moment, so don't have time to delve into the guts of the above myself at the moment, but somebody else may come along before I can get back...
However, from your above description, if you have boundaries of these areas defined so that you can use fill to color the areas desired, then perhaps polyshape and its companion area may solve your problem. They, too, will require the time axis variable be treated as a double, but if you have a set of vertices, the above may be more direct route to your goal.

Sign in to comment.

Answers (0)

Categories

Products

Release

R2020a

Asked:

on 11 Dec 2021

Commented:

dpb
on 15 Dec 2021

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!