Archived OpenModelica forums. Posting is disabled.

Alternative forums include GitHub discussions or StackOverflow (make sure to read the Stack Overflow rules; you need to have well-formed questions)


Forgot password? | Forgot username? | Register

Cumulative of time variables

Cumulative of time variables

I am new to modelica so apologies if this is a simple request. I am manipulating a series of y values derived from a time table and need to plot the value of their total as well as the values themselves. How can I create this cumulative value that corresponds to the time interval?

For example if I have a series of values 1,3,5,2,7 how can I generate their cumulative values 1,4,9,11,18?

Many thanks

Re: Cumulative of time variables

Remember that variables in Modelica are generally continuous.  So, they have to have a value between the points you listed below.  One way to do something similar to what you want is to just add an integrator.  But, then the range between the values will matter to the output.  So, make sure that it does what you want.  If you just use timeTable it uses a linear fit between each point.  An option is then to sample every time period of interest, for example every second, and then integrate that value.  Here is a quick example with those two different methods:

Code:

model IntegrateTest

  Modelica.Blocks.Continuous.Integrator integrator1 annotation(Placement(visible = true, transformation(origin = {4, 24}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Sources.TimeTable timeTable1(table = [0, 1; 1, 3; 2, 5; 3, 2; 4, 7; 5, 0; 8, 0]) annotation(Placement(visible = true, transformation(origin = {-46, 26}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Discrete.Sampler sampler1(samplePeriod = 1) annotation(Placement(visible = true, transformation(origin = {-18, -18}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Continuous.Integrator integrator2 annotation(Placement(visible = true, transformation(origin = {30, -20}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
equation
  connect(timeTable1.y, sampler1.u) annotation(Line(points = {{-35, 26}, {-32, 26}, {-32, -8}, {-48, -8}, {-48, -18}, {-30, -18}, {-30, -18}}, color = {0, 0, 127}));
  connect(timeTable1.y, integrator1.u) annotation(Line(points = {{-35, 26}, {-20, 26}, {-20, 24}, {-10, 24}}, color = {0, 0, 127}));
  connect(sampler1.y, integrator2.u) annotation(Line(points = {{-7, -18}, {6, -18}, {6, -20}, {18, -20}, {18, -20}}, color = {0, 0, 127}));
  annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})));
end IntegrateTest;

Re: Cumulative of time variables

Many thanks for this - the only issue I am now facing is that the integral always plots from 0. Is there any way I can get it to start from the first value in the table. Otherwise it is not truly cumulative.

I appreciate your help.

Re: Cumulative of time variables

You can just set y_start of the integrator to the value that you want to start with. 

Re: Cumulative of time variables

Hi.Thanks again and sorry to be a pain. I understand how y_start works with a fixed value but can I use the first time dependent variable value? It will vary so I cannot give it a value but I cannot work out the syntax to specify the input value at time =1.

For example if I have 10 samples u(time=1), u(time=2),.......u(time=10) I want to end up with u(time=1 + u(time=2)+........u(time=10)

Hope that makes sense. Again - any help appreciated.

thanks

Re: Cumulative of time variables

First off, remember that the data is considered essentially continuous.  That means that at time 1.5 it has to have a value.  It seems that you are trying to care about the data at each transition.  That said, my suggestion above seems to do what you want, but does it with a 1 second lag.  So, one option would be to move your data 1 second "earlier" and then you would get your expected results.

Re: Cumulative of time variables

Hi yes. I hear what you are saying. Basically I have a series on monthly production figures which are definitive for that month. Naturally there has to be a transition at say month 3.5 between month 3 and 4. The problem is that the cumulative value at end of month 1 is less than the value for the month itself. The attached plot illustrates the monthly values in blue and the total in red. Doesnt make sense over the early part of the timescale but probably don to the integration itself. Moving the origin is not going to help as we have to start from 0 in month 0. Any ideas?


https://www.openmodelica.org/images/agorapro/attachments/4611/mini_Sample-plots.jpg

Attachments:

Re: Cumulative of time variables

I think that this version should do what you seem to want.  Take a look at the output of timeTable1 versus the output of sumChange1:

Code:


model IntegrateTest
  Modelica.Blocks.Continuous.Integrator integrator1 annotation(Placement(visible = true, transformation(origin = {4, 24}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Sources.TimeTable timeTable1(table = [0, 1; 1, 3; 2, 5; 3, 2; 4, 7; 5, 0; 8, 0]) annotation(Placement(visible = true, transformation(origin = {-46, 26}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Discrete.Sampler sampler1(samplePeriod = 1) annotation(Placement(visible = true, transformation(origin = {-18, -18}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
  Modelica.Blocks.Continuous.Integrator integrator2 annotation(Placement(visible = true, transformation(origin = {30, -20}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));

  model SumChange
    extends Modelica.Blocks.Interfaces.SISO;
  equation
    when {not u == pre(u), initial()} then
      y = pre(y) + u;
    end when;
    annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})));
  end SumChange;

  SumChange sumChange1 annotation(Placement(visible = true, transformation(origin = {4, -54}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
equation
  connect(sampler1.y, sumChange1.u) annotation(Line(points = {{-7, -18}, {0, -18}, {0, -36}, {-24, -36}, {-24, -54}, {-10, -54}, {-10, -54}}, color = {0, 0, 127}));
  connect(sampler1.y, integrator2.u) annotation(Line(points = {{-7, -18}, {6, -18}, {6, -20}, {18, -20}}, color = {0, 0, 127}));
  connect(timeTable1.y, sampler1.u) annotation(Line(points = {{-35, 26}, {-32, 26}, {-32, -8}, {-48, -8}, {-48, -18}, {-30, -18}, {-30, -18}}, color = {0, 0, 127}));
  connect(timeTable1.y, integrator1.u) annotation(Line(points = {{-35, 26}, {-20, 26}, {-20, 24}, {-10, 24}}, color = {0, 0, 127}));
  annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), experiment(StartTime = 0, StopTime = 10, Tolerance = 1e-6, Interval = 0.02));
end IntegrateTest;

Re: Cumulative of time variables

Hi,

I think we are getting close but I get the following error both in OMEdit and Dymola:

Check of IntegrateTest:

It is not allowed to use pre for a continuous time variable outside a when clause:
pre(sumChange1.u)

The when-condition must be a discrete expression:
when not (sumChange1.u == pre(sumChange1.u)) then
sumChange1.y = pre(sumChange1.y)+sumChange1.u;
end when;

Error detected in
when not (sumChange1.u == pre(sumChange1.u)) then
sumChange1.y = pre(sumChange1.y)+sumChange1.u;
end when;

Errors detected in model.

Check aborted.

ERROR: 2 errors were found

Any suggestions?

Re: Cumulative of time variables

What version of OMEdit are you using?  I am asking because the code I proposed works fine for me.  So, there is a bug in my version or your version.  Right now I am running  1.9.4~dev-9.  I don't know why your version, and Dymola claim it is an error, while my new version of OMEdit seems to accept it fine.

This might work for you instead:

Code:


model IntegrateTest
  Modelica.Blocks.Sources.TimeTable timeTable1(table = [0, 1; 1, 3; 2, 5; 3, 2; 4, 7; 5, 0; 8, 0]) annotation(Placement(visible = true, transformation(origin = {-46, 26}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));

  model SumChange
    extends Modelica.Blocks.Interfaces.SISO;
  equation
    when {not u == pre(u), initial()} then
      y = pre(y) + u;
    end when;
    annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})));
  end SumChange;

  model SumTime
    extends Modelica.Blocks.Interfaces.SISO;
    Boolean sampleTrigger;
    parameter Modelica.SIunits.Time samplePeriod = 1.0;
  equation
    sampleTrigger = sample(0, samplePeriod);
    when sampleTrigger then
      y = pre(y) + u;
    end when;
    annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})));
  end SumTime;

  SumTime sumTime1 annotation(Placement(visible = true, transformation(origin = {-8, 68}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
equation
  connect(timeTable1.y, sumTime1.u) annotation(Line(points = {{-35, 26}, {-30, 26}, {-30, 68}, {-20, 68}, {-20, 68}}, color = {0, 0, 127}));
  annotation(Icon(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), Diagram(coordinateSystem(extent = {{-100, -100}, {100, 100}}, preserveAspectRatio = true, initialScale = 0.1, grid = {2, 2})), experiment(StartTime = 0, StopTime = 10, Tolerance = 1e-6, Interval = 0.02));
end IntegrateTest;

Re: Cumulative of time variables

Hi.

I think we have a winner. All works fine. Many thanks.BTW I am using OE 1.9.1 (r22929) (RML version) and Dymola Version 2015 64bit.

You have been very helpful - I have learnt a lot and appreciate it.

Thanks

Re: Cumulative of time variables

It looks like my use of pre(), in my earlier version, works in OM, but is outside the Modelica spec.  See:
pre() operator
Determine min max
Determine min max

And an answer here that does solve the problem:
Detect change

However, using pre, or the version in the link above, would actually miss any months that happened to have the same values, since there would be no change.  While sampling, as in my prior answers, will get every change (assuming that you have data for every month, and set the correct sampling interval)

Re: Cumulative of time variables

It looks like my use of pre(), in my earlier version, works in OM, but is outside the Modelica spec.  See:
pre() operator
Determine min max
Determine min max

And an answer here that does solve the problem:
Detect change

However, using pre, or the version in the link above, would actually miss any months that happened to have the same values, since there would be no change.  While sampling, as in my prior answers, will get every change (assuming that you have data for every month, and set the correct sampling interval)

There are 0 guests and 0 other users also viewing this topic
You are here: