Hello,
I am not sure what cumtrapz does. So I have a plot.
There are 3 plots. First is power which is Kilo Watts. Second and Third are energy. But Energy calculated just as kilowatt into hour and second cumtrapz(power) * time which is hour. I was expecting both of those plots to be same. Which means I dont understand cumtrapz correctly. What does cumtrapz do? Thank you.

 Accepted Answer

"What does cumtrapz do?"
cumtrapz(y, x) performs cumulative numerical integration using the trapezoidal rule. It calculates the cumulative area under the curve y(x) from the start up to each point. If your power is in kilowatts (kW) and time is in hours, then:
  • cumtrapz(time, power) gives you energy in kWh (kilowatt-hours)
  • This is because ∫P(t)dt = Energy, and the units work out: kW × hours = kWh
"Which means I dont understand cumtrapz correctly"
There are actually several problems here:
  1. Second plot: Power × Time - This is NOT energy! This would have units of kW×h², which is meaningless physically. If you're multiplying power by the time vector element-wise, you're getting something that grows much faster than energy should.
  2. Third plot: cumtrapz(Power) × Time - This is also wrong: you are taking the cumulative integral of power (which gives energy), then multiplying by time again, giving you units of kWh×h = kWh².
Try plotting just cumtrapz(time, power) to see the actual energy consumption. I will demonstrate with some fake data (this would be much easier if you uploaded some sample data):
T = 0:100:18000;
P = min(120, max(90+(140-90)*(1-T/8500), 90+(140-90)*(T-9500)/8500));
plot(T,P)
E = cumtrapz(T,P);
plot(T,E)

7 Comments

by the way i made a mistake when I said energy is equal to cumtrapz(power) * time. Its not time. Its dt, the difference in time which is 1 second converted to hour that is 1/3600 and then it is plotted over time. So is that correct.
I see, now I know why the formula is applied. It only works for constant power.
Stephen23
Stephen23 on 18 Sep 2025
Edited: Stephen23 on 19 Sep 2025
"i made a mistake when I said energy is equal to cumtrapz(power) * time. Its not time. Its dt, the difference in time which is 1 second converted to hour that is 1/3600 and then it is plotted over time. So is that correct"
When power varies over time, energy should be calculated as:
Energy = ∫ Power(t) dt
Your approach of cumtrapz(power)*dt assumes that you can factor out dt from the integral, which would only be valid if dt is constant.
The correct approaches:
  1. Proper method: cumtrapz(time,power) - This accounts for the actual time spacing and varying power levels using trapezoidal integration.
  2. Only valid for uniform time spacing: cumsum(power)*dt - can be reasonable if your time steps are small and uniform.
Why your plots differ:
  • Plot 2 power*time: This is just power multiplied by elapsed time, not energy integration
  • Plot 3 cumtrapz(power)*dt: This uses trapezoidal approximation with constant dt
  • Best: cumtrapz(time, power) for any time spacing
"Plot 3 (cumtrapz(power) * dt): This uses rectangular approximation with constant dt"
cumtrapz use rectangular integration?
"Your approach of cumtrapz(power) * dt assumes that you can factor out dt from the integral, which would only be valid if power were constant. "
Why wouldn't cumtrapz(power)*dt be valid in general (with uniform time spacing)? The area of each trapezoid is proportional to dt, so factoring dt out of the sum and shouldn't matter (as shown on the cumtrapz doc page)
T = 0:100:18000;
P = min(120, max(90+(140-90)*(1-T/8500), 90+(140-90)*(T-9500)/8500));
E = cumtrapz(T,P);
dt = T(2);
figure
plot(T,E,T,cumtrapz(P)*dt)
legend('cumtrapz(T,P)','cumtrapz(P)*dt')
@Paul: thank you, I fixed the reference to trapezoidal approximation.
If the time steps are constant and small then cumtrapz(P)*dT might be a reasonable approximation... but personally I would avoid this with real-world data (unless there is a truly compelling reason to use it). Assuming perfectly constant timesteps across hundreds/thousands/millions of data samples and absolutely no missing samples... sure, just like all of those threads where the OP promises that they have checked their huge data file and it really is perfect and there is no way it contains anything other than numeric data...
Using cumtrapz(T,P) works, is (likely) not particularly slower than cumtrapz(P)*dT, and adjusts to the users real-world sampling without any further effort. Strongly recommended.
"Strongly recommended"
No disagreement there, it's what I've always used.
"If the time steps are constant and small then cumtrapz(P)*dT might be a reasonable approximation"
Why the emphasis on "small"? And, reasonable approximation to what? From the context, perhaps you mean that cumtrapz(P)*dT might be a reasonable approximation to cumtrapz(T,P) when T is not uniformly spaced and dt is an average spacing? But I don't think anywhere in this thread is it suggested to use anything other than cumtrapz(T,P) when T is not uniformly spaced, so maybe I'm missing the point of that statement.
For what it's worth, one can encounter situations where the system under test samples measurements at (essentially) a constant sampling rate, but the data acquisition system can introduce errors in assigning time tags to the data that makes the collected data appear to be nonuniformly sampled.
"reasonable approximation to what?"
The real-world energy.
"Why the emphasis on "small"?"
Experience working with lots of data: larger steps generally give a larger output error range, but this depends on the measurement error. Applies of course to all cumtrapz usage.
"perhaps you mean that cumtrapz(P)*dT might be a reasonable approximation to cumtrapz(T,P)"
Both are approximations of the real-world energy.

Sign in to comment.

More Answers (1)

cumtrapz() is used to approximate the cumulative trapezoidal numerical integration.
For example, .
x = linspace(-2, 2, 401);
y = cumtrapz(x(201:401), 2*x(201:401));
hold on
plot(x, x.^2, '--') % blue dashed curve
plot(x(201:401), y), grid on % red solid curve
legend('x^{2}', 'cumtrapz', 'location', 'north')
hold off

2 Comments

Here is a minor update. I believe this is the method you intended to implement in the 3rd plot.
x = linspace(-2, 2, 401);
A = zeros(1, 201); % initialization
dt = x(2) - x(1); % step length
for i = 202:401
% y(i-200) = trapz(x(201:i), 2*x(201:i));
% y(i-200) = trapz(2*x(201:i))*dt;
A(i-200) = trapz(2*x(i-1:i));
end
hold on
plot(x, x.^2, '--') % blue dashed curve
plot(x(201:401), cumsum(A)*dt), grid on % red solid curve
legend('x^{2}', 'cumsum(A)·dt', 'location', 'north')
hold off
xlabel('x')
ylabel('y')

Sign in to comment.

Categories

Tags

Community Treasure Hunt

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

Start Hunting!