integrator_export.cpp
Go to the documentation of this file.
1 /*
2  * This file is part of ACADO Toolkit.
3  *
4  * ACADO Toolkit -- A Toolkit for Automatic Control and Dynamic Optimization.
5  * Copyright (C) 2008-2014 by Boris Houska, Hans Joachim Ferreau,
6  * Milan Vukov, Rien Quirynen, KU Leuven.
7  * Developed within the Optimization in Engineering Center (OPTEC)
8  * under supervision of Moritz Diehl. All rights reserved.
9  *
10  * ACADO Toolkit is free software; you can redistribute it and/or
11  * modify it under the terms of the GNU Lesser General Public
12  * License as published by the Free Software Foundation; either
13  * version 3 of the License, or (at your option) any later version.
14  *
15  * ACADO Toolkit is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18  * Lesser General Public License for more details.
19  *
20  * You should have received a copy of the GNU Lesser General Public
21  * License along with ACADO Toolkit; if not, write to the Free Software
22  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
23  *
24  */
25 
26 
27 
35 
36 
37 using namespace std;
38 
40 
41 //
42 // PUBLIC MEMBER FUNCTIONS:
43 //
44 
46  const std::string& _commonHeaderName
47  ) : ExportAlgorithm( _userInteraction,_commonHeaderName )
48 {
49  NX1 = 0;
50  NX2 = 0;
51  NX3 = 0;
52 
53  NDX3 = 0;
54  NXA3 = 0;
55 
56  timeDependant = false;
57 
58  exportRhs = true;
59  crsFormat = false;
60 
61  reset_int = ExportVariable( "resetIntegrator", 1, 1, INT, ACADO_LOCAL, true );
62  error_code = ExportVariable( "error", 1, 1, INT, ACADO_LOCAL, true );
63 }
64 
65 
67  ) : ExportAlgorithm( arg )
68 {
69  NX1 = arg.NX1;
70  NX2 = arg.NX2;
71  NX3 = arg.NX3;
72 
73  NDX3 = arg.NDX3;
74  NXA3 = arg.NXA3;
75 
76  timeDependant = false;
77 
78  exportRhs = true;
79  crsFormat = false;
80 }
81 
82 
84 {
85  clear( );
86 }
87 
88 
90  )
91 {
92  if( this != &arg && &arg != 0 )
93  {
94  clear( );
96  }
97  return *this;
98 }
99 
100 
102 {
103  grid = _grid;
104 
105  return SUCCESSFUL_RETURN;
106 }
107 
108 
110 {
111  if( !A1.isEmpty() ) {
112  LOG( LVL_DEBUG ) << "Integrator: setLinearInput... " << endl;
113  if( A1.getNumRows() != M1.getNumRows() || A1.getNumRows() != B1.getNumRows() || A1.getNumRows() != A1.getNumCols() || M1.getNumRows() != M1.getNumCols() || B1.getNumCols() != NU) {
115  }
116  NX1 = A1.getNumRows();
117  M11 = M1;
118  A11 = A1;
119  B11 = B1;
120 
121  OnlineData dummy0;
122  Control dummy1;
123  DifferentialState dummy2;
124  dummy0.clearStaticCounters();
125  dummy1.clearStaticCounters();
126  dummy2.clearStaticCounters();
127  x = DifferentialState("", NX1, 1);
128  u = Control("", NU, 1);
129  od = OnlineData("", NOD, 1);
130 
131  DifferentialEquation fun_input;
132  fun_input << A11*x+B11*u;
133  lin_input.init(fun_input, "acado_linear_input", NX, NXA, NU);
134  LOG( LVL_DEBUG ) << "done!" << endl;
135  }
136 
137  return SUCCESSFUL_RETURN;
138 }
139 
140 
141 returnValue IntegratorExport::setModel( const std::string& _name_ODE, const std::string& _name_diffs_ODE ) {
142 
143  if( rhs.getFunctionDim() == 0 ) {
144  rhs = ExportAcadoFunction(_name_ODE);
145  diffs_rhs = ExportAcadoFunction(_name_diffs_ODE);
146 
147  exportRhs = false;
148  }
149  else {
150  return ACADOERROR( RET_INVALID_OPTION );
151  }
152 
153  OnlineData dummy0;
154  Control dummy1;
155  DifferentialState dummy2;
156  AlgebraicState dummy3;
158  dummy0.clearStaticCounters();
159  dummy1.clearStaticCounters();
160  dummy2.clearStaticCounters();
161  dummy3.clearStaticCounters();
162  dummy4.clearStaticCounters();
163 
164  NX2 = NX-NX1-NX3;
165 
166  x = DifferentialState("", NX, 1);
168  z = AlgebraicState("", NXA, 1);
169  u = Control("", NU, 1);
170  od = OnlineData("", NOD, 1);
171 
172  return SUCCESSFUL_RETURN;
173 }
174 
175 
177 {
178  if( !A3.isEmpty() ) {
179  if( A3.getNumRows() != M3.getNumRows() || M3.getNumRows() != M3.getNumCols() || A3.getNumRows() != A3.getNumCols() || A3.getNumRows() != _rhs.getDim() ) {
181  }
182  NX3 = A3.getNumRows();
183  M33 = M3;
184  A33 = A3;
185 
186  OutputFcn f;
187  f << _rhs;
188  OnlineData dummy0;
189  Control dummy1;
190  DifferentialState dummy2;
191  AlgebraicState dummy3;
193  dummy0.clearStaticCounters();
194  dummy1.clearStaticCounters();
195  dummy2.clearStaticCounters();
196  x = DifferentialState("", NX1+NX2, 1);
197  u = Control("", NU, 1);
198  od = OnlineData("", NOD, 1);
199 
200  if( (uint)f.getNX() > (NX1+NX2) ) {
202  }
203  if( (uint)f.getNDX() > (NX1+NX2) ) {
205  }
206  if( f.getNDX() > 0 ) {
207  NDX3 = NX1+NX2;
208  NDX = NX;
209  }
210  else NDX3 = 0;
211 
212  dummy4.clearStaticCounters();
214 
215  if( f.getNXA() > 0 && NXA == 0 ) {
217  }
218  if( f.getNXA() > 0 ) NXA3 = NXA;
219  else NXA3 = 0;
220  dummy3.clearStaticCounters();
221  z = AlgebraicState("", NXA3, 1);
222 
223  uint i;
224  OutputFcn g;
225  for( i = 0; i < _rhs.getDim(); i++ ) {
226  g << forwardDerivative( _rhs(i), x );
227  g << forwardDerivative( _rhs(i), z );
228  g << forwardDerivative( _rhs(i), u );
229  g << forwardDerivative( _rhs(i), dx );
230  }
231 
232  dummy2.clearStaticCounters();
233  x = DifferentialState("", NX, 1);
234 
235  DMatrix dependencyMat = _rhs.getDependencyPattern( x );
236  DVector dependency = dependencyMat.sumRow( );
237  for( i = NX1+NX2; i < NX; i++ ) {
238  if( acadoRoundAway(dependency(i)) != 0 ) { // This expression should not depend on these differential states
240  }
241  }
242 
243  OutputFcn f_large;
244  DMatrix A3_large = expandOutputMatrix(A3);
245  f_large << _rhs + A3_large*x;
246 
247  return (rhs3.init(f_large, "rhs3", NX, NXA, NU, NP, NDX, NOD) &
248  diffs_rhs3.init(g, "diffs3", NX, NXA, NU, NP, NDX, NOD));
249  }
250 
251  return SUCCESSFUL_RETURN;
252 }
253 
254 
256 {
257  if( !C.isEmpty() ) {
259  }
260  else {
261  return SUCCESSFUL_RETURN;
262  }
263 }
264 
265 
266 returnValue IntegratorExport::setLinearOutput( const DMatrix& M3, const DMatrix& A3, const std::string& _rhs3, const std::string& _diffs_rhs3 )
267 {
268  if( !A3.isEmpty() ) {
269  if( A3.getNumRows() != M3.getNumRows() || M3.getNumRows() != M3.getNumCols() || A3.getNumRows() != A3.getNumCols() ) {
271  }
272  NX3 = A3.getNumRows();
273  M33 = M3;
274  A33 = A3;
275 
276  rhs3 = ExportAcadoFunction(_rhs3);
277  diffs_rhs3 = ExportAcadoFunction(_diffs_rhs3);
278  exportRhs = false;
279 
280  OnlineData dummy0;
281  Control dummy1;
282  DifferentialState dummy2;
283  AlgebraicState dummy3;
285  dummy0.clearStaticCounters();
286  dummy1.clearStaticCounters();
287  dummy2.clearStaticCounters();
288  dummy3.clearStaticCounters();
289  dummy4.clearStaticCounters();
290 
291  x = DifferentialState("", NX, 1);
293  z = AlgebraicState("", NXA, 1);
294  u = Control("", NU, 1);
295  od = OnlineData("", NOD, 1);
296  }
297 
298  return SUCCESSFUL_RETURN;
299 }
300 
301 
303 
304  LOG( LVL_DEBUG ) << "Integrator: setup model data... " << endl;
305  setDimensions( data.getNX(),data.getNDX(),data.getNXA(),data.getNU(),data.getNP(),data.getN(), data.getNOD() );
306  NX1 = data.getNX1();
307  NX2 = data.getNX2();
308  NX3 = data.getNX3();
309  NDX3 = data.getNDX3();
310  NXA3 = data.getNXA3();
311  exportRhs = data.exportRhs();
312 
313  Grid integrationGrid;
314  data.getIntegrationGrid(integrationGrid);
315  grid = integrationGrid;
316  data.getNumSteps( numSteps );
317 
318  DMatrix M1, A1, B1;
319  data.getLinearInput( M1, A1, B1 );
320  if ( M1.getNumRows() > 0 && setLinearInput( M1, A1, B1 ) != SUCCESSFUL_RETURN )
322 
323  DMatrix M3, A3;
324  data.getLinearOutput( M3, A3 );
325 
326  if( exportRhs ) {
328  data.getModel(f);
329  if(f.getDim() > 0 && f.getNDX() == 0) {
331  for( uint i = 0; i < order.getDim(); i++ ) {
332 // std::cout << "NX1+i: " << NX1+i << ", order(i): " << order(i) << std::endl;
333  if( (NX1+i) != (uint)order(i) ) {
334  return ACADOERRORTEXT(RET_NOT_IMPLEMENTED_YET, "The order of defined state variables should correspond to the order of equations in case of an explicit system!");
335  }
336  }
337  }
338 
339  OutputFcn f3;
340  data.getLinearOutput( M3, A3, f3 );
341  DMatrix parms;
342  uint delay;
343  data.getNARXmodel( delay, parms );
344 
345  Expression rhs_, rhs3_;
346  f.getExpression( rhs_ );
347  f3.getExpression( rhs3_ );
348 
349  // Nonlinear feedback function:
350  DMatrix C;
351  OutputFcn feedb;
352  data.getNonlinearFeedback( C, feedb );
353  Expression feedb_;
354  feedb.getExpression( feedb_ );
355 
356  if ( f.getDim() > 0 && setDifferentialEquation( rhs_ ) != SUCCESSFUL_RETURN )
358  if ( !parms.isEmpty() && setNARXmodel( delay, parms ) != SUCCESSFUL_RETURN )
360  if ( M3.getNumRows() > 0 && setLinearOutput( M3, A3, rhs3_ ) != SUCCESSFUL_RETURN )
362  if ( C.getNumCols() > 0 && setNonlinearFeedback( C, feedb_ ) != SUCCESSFUL_RETURN )
364  }
365  else {
366  if ( M3.getNumRows() > 0 && setLinearOutput( M3, A3, data.getNameOutput(), data.getNameDiffsOutput() ) != SUCCESSFUL_RETURN )
368  if ( setModel( data.getNameRhs(), data.getNameDiffsRhs() ) != SUCCESSFUL_RETURN )
370  }
371 
372  setup( );
373 
374  if( data.hasOutputs() ) {
375  std::vector<Grid> outputGrids_;
376  data.getOutputGrids(outputGrids_);
377  std::vector<Expression> outputExpressions_;
378  data.getOutputExpressions(outputExpressions_);
379 
380  if( outputExpressions_.size() > 0 ) {
381  setupOutput( outputGrids_, outputExpressions_ );
382  }
383  else {
384  std::vector<std::string> outputNames;
385  std::vector<std::string> diffs_outputNames;
386  std::vector<uint> dim_outputs;
387  std::vector<DMatrix> outputDependencies_ = data.getOutputDependencies();
388  data.getNameOutputs(outputNames);
389  data.getNameDiffsOutputs(diffs_outputNames);
390  data.getDimOutputs(dim_outputs);
391  if( !data.hasCompressedStorage() ) {
392  setupOutput( outputGrids_, outputNames, diffs_outputNames, dim_outputs );
393  }
394  else {
395  setupOutput( outputGrids_, outputNames, diffs_outputNames, dim_outputs, outputDependencies_ );
396  }
397  }
398  }
399 
400  setup( );
401  LOG( LVL_DEBUG ) << "done!" << endl;
402 
403  return SUCCESSFUL_RETURN;
404 }
405 
406 
408 {
409  if( NX1 > 0 ) {
410  ExportForLoop loop01( index1,0,NX1 );
411  ExportForLoop loop02( index2,0,NX1 );
412  loop02.addStatement( tmp_index == index2+index1*NX );
413  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew1.getSubMatrix( index1,index1+1,index2,index2+1 ) );
414  loop01.addStatement( loop02 );
415 
416  if( NU > 0 ) {
417  ExportForLoop loop03( index2,0,NU );
418  loop03.addStatement( tmp_index == index2+index1*NU );
419  loop03.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew1.getSubMatrix( index1,index1+1,NX1+index2,NX1+index2+1 ) );
420  loop01.addStatement( loop03 );
421  }
422  block->addStatement( loop01 );
423  }
424 
425  return SUCCESSFUL_RETURN;
426 }
427 
428 
430  const ExportIndex& index3, const ExportIndex& tmp_index )
431 {
432  if( NX1 > 0 ) {
433  ExportForLoop loop01( index1,0,NX1 );
434  ExportForLoop loop02( index2,0,NX1 );
435  loop02.addStatement( tmp_index == index2+index1*NX );
436  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew1.getSubMatrix( index1,index1+1,0,1 )*rk_diffsPrev1.getSubMatrix( 0,1,index2,index2+1 ) );
437  ExportForLoop loop03( index3,1,NX1 );
438  loop03.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew1.getSubMatrix( index1,index1+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,index2,index2+1 ) );
439  loop02.addStatement( loop03 );
440  loop01.addStatement( loop02 );
441 
442  if( NU > 0 ) {
443  ExportForLoop loop04( index2,0,NU );
444  loop04.addStatement( tmp_index == index2+index1*NU );
445  loop04.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew1.getSubMatrix( index1,index1+1,NX1+index2,NX1+index2+1 ) );
446  ExportForLoop loop05( index3,0,NX1 );
447  loop05.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew1.getSubMatrix( index1,index1+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,NX1+index2,NX1+index2+1 ) );
448  loop04.addStatement( loop05 );
449  loop01.addStatement( loop04 );
450  }
451  block->addStatement( loop01 );
452  }
453  return SUCCESSFUL_RETURN;
454 }
455 
456 
458 {
459  if( NX2 > 0 ) {
460  ExportForLoop loop01( index1,NX1,NX1+NX2 );
461  ExportForLoop loop02( index2,0,NX1+NX2 );
462  loop02.addStatement( tmp_index == index2+index1*NX );
463  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,index2,index2+1 ) );
464  loop01.addStatement( loop02 );
465 
466  if( NU > 0 ) {
467  ExportForLoop loop03( index2,0,NU );
468  loop03.addStatement( tmp_index == index2+index1*NU );
469  loop03.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1+NX2+index2,NX1+NX2+index2+1 ) );
470  loop01.addStatement( loop03 );
471  }
472  block->addStatement( loop01 );
473  }
474  // ALGEBRAIC STATES
475  if( NXA > 0 ) {
476  ExportForLoop loop01( index1,NX,NX+NXA );
477  ExportForLoop loop02( index2,0,NX1+NX2 );
478  loop02.addStatement( tmp_index == index2+index1*NX );
479  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew2.getSubMatrix( index1-NX1-NX3,index1-NX1-NX3+1,index2,index2+1 ) );
480  loop01.addStatement( loop02 );
481 
482  if( NU > 0 ) {
483  ExportForLoop loop03( index2,0,NU );
484  loop03.addStatement( tmp_index == index2+index1*NU );
485  loop03.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew2.getSubMatrix( index1-NX1-NX3,index1-NX1-NX3+1,NX1+NX2+index2,NX1+NX2+index2+1 ) );
486  loop01.addStatement( loop03 );
487  }
488  block->addStatement( loop01 );
489  }
490 
491  return SUCCESSFUL_RETURN;
492 }
493 
494 
496  const ExportIndex& _index3, const ExportIndex& tmp_index )
497 {
498  uint index3; // index3 instead of _index3 to unroll loops
499  if( NX2 > 0 ) {
500  ExportForLoop loop01( index1,NX1,NX1+NX2 );
501  if( NX1 > 0 ) {
502  ExportForLoop loop02( index2,0,NX1 );
503  loop02.addStatement( tmp_index == index2+index1*NX );
504  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,0,1 )*rk_diffsPrev1.getSubMatrix( 0,1,index2,index2+1 ) );
505  for( index3 = 1; index3 < NX1; index3++ ) {
506  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,index2,index2+1 ) );
507  }
508  for( index3 = 0; index3 < NX2; index3++ ) {
509  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,index2,index2+1 ) );
510  }
511  loop01.addStatement( loop02 );
512  }
513 
514  ExportForLoop loop05( index2,NX1,NX1+NX2 );
515  loop05.addStatement( tmp_index == index2+index1*NX );
516  loop05.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1,NX1+1 )*rk_diffsPrev2.getSubMatrix( 0,1,index2,index2+1 ) );
517  for( index3 = 1; index3 < NX2; index3++ ) {
518  loop05.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,index2,index2+1 ) );
519  }
520  loop01.addStatement( loop05 );
521 
522  if( NU > 0 ) {
523  ExportForLoop loop07( index2,0,NU );
524  loop07.addStatement( tmp_index == index2+index1*NU );
525  loop07.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1+NX2+index2,NX1+NX2+index2+1 ) );
526  for( index3 = 0; index3 < NX1; index3++ ) {
527  loop07.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,NX1+index2,NX1+index2+1 ) );
528  }
529  for( index3 = 0; index3 < NX2; index3++ ) {
530  loop07.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew2.getSubMatrix( index1-NX1,index1-NX1+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,NX1+NX2+index2,NX1+NX2+index2+1 ) );
531  }
532  loop01.addStatement( loop07 );
533  }
534  block->addStatement( loop01 );
535  }
536  // ALGEBRAIC STATES: NO PROPAGATION OF SENSITIVITIES NEEDED
537 
538  return SUCCESSFUL_RETURN;
539 }
540 
541 
543 {
544  if( NX3 > 0 ) {
545  ExportForLoop loop01( index1,NX1+NX2,NX );
546  ExportForLoop loop02( index2,0,NX );
547  loop02.addStatement( tmp_index == index2+index1*NX );
548  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,index2,index2+1 ) );
549  loop01.addStatement( loop02 );
550 
551  if( NU > 0 ) {
552  ExportForLoop loop03( index2,0,NU );
553  loop03.addStatement( tmp_index == index2+index1*NU );
554  loop03.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX+index2,NX+index2+1 ) );
555  loop01.addStatement( loop03 );
556  }
557  block->addStatement( loop01 );
558  }
559 
560  return SUCCESSFUL_RETURN;
561 }
562 
563 
565  const ExportIndex& index3, const ExportIndex& tmp_index )
566 {
567  if( NX3 > 0 ) {
568  ExportForLoop loop01( index1,NX1+NX2,NX );
569  ExportForLoop loop02( index2,0,NX1 );
570  loop02.addStatement( tmp_index == index2+index1*NX );
571  loop02.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == 0.0 );
572  ExportForLoop loop03( index3,0,NX1 );
573  loop03.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,index2,index2+1 ) );
574  loop02.addStatement( loop03 );
575  ExportForLoop loop04( index3,0,NX2 );
576  loop04.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,index2,index2+1 ) );
577  loop02.addStatement( loop04 );
578  ExportForLoop loop042( index3,0,NX3 );
579  loop042.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+NX2+index3,NX1+NX2+index3+1 )*rk_diffsPrev3.getSubMatrix( index3,index3+1,index2,index2+1 ) );
580  loop02.addStatement( loop042 );
581  loop01.addStatement( loop02 );
582 
583  ExportForLoop loop05( index2,NX1,NX1+NX2 );
584  loop05.addStatement( tmp_index == index2+index1*NX );
585  loop05.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == 0.0 );
586  ExportForLoop loop06( index3,0,NX2 );
587  loop06.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,index2,index2+1 ) );
588  loop05.addStatement( loop06 );
589  ExportForLoop loop062( index3,0,NX3 );
590  loop062.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+NX2+index3,NX1+NX2+index3+1 )*rk_diffsPrev3.getSubMatrix( index3,index3+1,index2,index2+1 ) );
591  loop05.addStatement( loop062 );
592  loop01.addStatement( loop05 );
593 
594  ExportForLoop loop07( index2,NX1+NX2,NX );
595  loop07.addStatement( tmp_index == index2+index1*NX );
596  loop07.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) == 0.0 );
597  ExportForLoop loop08( index3,0,NX3 );
598  loop08.addStatement( rk_eta.getCol( tmp_index+NX+NXA ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+NX2+index3,NX1+NX2+index3+1 )*rk_diffsPrev3.getSubMatrix( index3,index3+1,index2,index2+1 ) );
599  loop07.addStatement( loop08 );
600  loop01.addStatement( loop07 );
601 
602  if( NU > 0 ) {
603  ExportForLoop loop09( index2,0,NU );
604  loop09.addStatement( tmp_index == index2+index1*NU );
605  loop09.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) == rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX+index2,NX+index2+1 ) );
606  ExportForLoop loop10( index3,0,NX1 );
607  loop10.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,index3,index3+1 )*rk_diffsPrev1.getSubMatrix( index3,index3+1,NX1+index2,NX1+index2+1 ) );
608  loop09.addStatement( loop10 );
609  ExportForLoop loop11( index3,0,NX2 );
610  loop11.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+index3,NX1+index3+1 )*rk_diffsPrev2.getSubMatrix( index3,index3+1,NX1+NX2+index2,NX1+NX2+index2+1 ) );
611  loop09.addStatement( loop11 );
612  ExportForLoop loop112( index3,0,NX3 );
613  loop112.addStatement( rk_eta.getCol( tmp_index+(NX+NXA)*(1+NX) ) += rk_diffsNew3.getSubMatrix( index1-NX1-NX2,index1-NX1-NX2+1,NX1+NX2+index3,NX1+NX2+index3+1 )*rk_diffsPrev3.getSubMatrix( index3,index3+1,NX+index2,NX+index2+1 ) );
614  loop09.addStatement( loop112 );
615  loop01.addStatement( loop09 );
616  }
617  block->addStatement( loop01 );
618  }
619 
620  return SUCCESSFUL_RETURN;
621 }
622 
623 
624 
625 // PROTECTED:
626 
627 
629  DMatrix result = zeros<double>(NX3,NX);
630  uint i,j;
631  for( i = 0; i < NX3; i++ ) {
632  for( j = 0; j < NX3; j++ ) {
633  result(i,NX-NX3+j) = A3(i,j);
634  }
635  }
636 
637  return result;
638 }
639 
640 
642  )
643 {
644  exportRhs = arg.exportRhs;
645  crsFormat = arg.crsFormat;
646  grid = arg.grid;
647  numSteps = arg.numSteps;
648 
649  // ExportFunctions
650  integrate = arg.integrate;
651 
652  return SUCCESSFUL_RETURN;
653 }
654 
655 
657 {
658  return SUCCESSFUL_RETURN;
659 }
660 
661 
663  uint index = 0;
664  double scale = 1.0/(grid.getLastTime() - grid.getFirstTime());
665  while( index < (grid.getNumIntervals()-1) && time > scale*grid.getTime( index+1 ) ) {
666  index++;
667  }
668  return index;
669 }
670 
671 
673 
674  grid_ = grid;
675  return SUCCESSFUL_RETURN;
676 }
677 
678 
680 
681  _numSteps = numSteps;
682  return SUCCESSFUL_RETURN;
683 }
684 
685 
686 returnValue IntegratorExport::getOutputExpressions( std::vector<Expression>& outputExpressions_ ) const{
687 
688  outputExpressions_ = outputExpressions;
689  return SUCCESSFUL_RETURN;
690 }
691 
692 
693 returnValue IntegratorExport::getOutputGrids( std::vector<Grid>& outputGrids_ ) const{
694 
695  outputGrids_ = outputGrids;
696  return SUCCESSFUL_RETURN;
697 }
698 
700 
701  return numSteps.isEmpty();
702 }
703 
704 const std::string IntegratorExport::getNameRHS() const{
705  return rhs.getName();
706 }
707 
708 const std::string IntegratorExport::getNameFullRHS() const{
709  if( NX2 == NX ) {
710  return getNameRHS();
711  }
712  else {
713  return fullRhs.getName();
714  }
715 }
716 
717 const std::string IntegratorExport::getNameOutputRHS() const{
718  return rhs3.getName();
719 }
720 
721 const std::string IntegratorExport::getNameOutputDiffs() const{
722  return diffs_rhs3.getName();
723 }
724 
725 const std::string IntegratorExport::getNameOUTPUT( uint index ) const{
726  return outputs[index].getName();
727 }
728 
730  if( exportRhs ) {
731  return outputExpressions[index].getDim();
732  }
733  else {
734  return num_outputs[index];
735  }
736 }
737 
738 
739 const std::string IntegratorExport::getNameDiffsRHS() const{
740  return diffs_rhs.getName();
741 }
742 
743 const std::string IntegratorExport::getNameDiffsOUTPUT( uint index ) const{
744  return diffs_outputs[index].getName();
745 }
746 
747 
749 
750 // end of file.
ExportVariable rk_diffsPrev1
returnValue setDimensions(uint _NX=0, uint _NU=0, uint _NP=0, uint _NI=0, uint _NOD=0)
#define LOG(level)
Just define a handy macro for getting the logger.
virtual returnValue setLinearOutput(const DMatrix &M3, const DMatrix &A3, const Expression &rhs)
Lowest level, the debug level.
uint getIntegrationInterval(double time)
bool isEmpty() const
Definition: matrix.hpp:193
#define B1
Allows to setup and evaluate output functions based on SymbolicExpressions.
Definition: output_fcn.hpp:55
virtual returnValue getNumSteps(DVector &_numSteps) const
double getTime(uint pointIdx) const
returnValue getNonlinearFeedback(DMatrix &C_, OutputFcn &feedb_) const
Definition: model_data.cpp:237
std::vector< DMatrix > getOutputDependencies() const
Definition: model_data.cpp:173
double getFirstTime() const
DVector getDimOutputs() const
Definition: model_data.cpp:591
returnValue getOutputExpressions(std::vector< Expression > &outputExpressions_) const
Definition: model_data.cpp:166
std::vector< Grid > outputGrids
DVector getDifferentialStateComponents() const
Allows to export code of an ACADO function.
virtual returnValue updateImplicitSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &tmp_index)
ExportAcadoFunction diffs_rhs
int getNDX() const
Definition: function.cpp:217
std::vector< ExportAcadoFunction > outputs
ExportVariable rk_diffsPrev3
Allows to pass back messages to the calling function.
virtual returnValue setModel(const std::string &_name_ODE, const std::string &_name_diffs_ODE)
DifferentialState x
Expression forwardDerivative(const Expression &arg1, const Expression &arg2)
AlgorithmicBase & operator=(const AlgorithmicBase &rhs)
virtual returnValue setGrid(const Grid &_grid)
Block< Derived > block(Index startRow, Index startCol, Index blockRows, Index blockCols)
Definition: BlockMethods.h:56
returnValue getModel(DifferentialEquation &_f) const
Definition: model_data.cpp:203
const std::string getNameOUTPUT(uint index) const
virtual returnValue propagateImplicitSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &_index3, const ExportIndex &tmp_index)
BEGIN_NAMESPACE_ACADO typedef unsigned int uint
Definition: acado_types.hpp:42
std::vector< ExportAcadoFunction > diffs_outputs
ExportVariable rk_diffsPrev2
Allows to conveniently handle (one-dimensional) grids consisting of time points.
Definition: grid.hpp:58
DMatrix expandOutputMatrix(const DMatrix &A3)
#define A1
Allows to export code of a for-loop.
const std::string getNameDiffsOUTPUT(uint index) const
const std::string getNameOutputDiffs() const
virtual returnValue setNonlinearFeedback(const DMatrix &C, const Expression &feedb)
#define CLOSE_NAMESPACE_ACADO
ExportVariable rk_diffsNew3
bool isEmpty() const
Definition: vector.hpp:176
Data class for defining models and everything that is related, to be passed to the integrator...
Definition: model_data.hpp:52
int getNXA() const
Definition: function.cpp:212
ExportVariable getSubMatrix(const ExportIndex &rowIdx1, const ExportIndex &rowIdx2, const ExportIndex &colIdx1, const ExportIndex &colIdx2) const
returnValue getExpression(Expression &expression) const
Definition: function.cpp:139
const std::string getNameDiffsRHS() const
returnValue getLinearOutput(DMatrix &M3_, DMatrix &A3_, OutputFcn &rhs_) const
Definition: model_data.cpp:228
Defines a scalar-valued index variable to be used for exporting code.
virtual returnValue setNARXmodel(const uint delay, const DMatrix &parms)=0
uint getNXA3() const
Definition: model_data.cpp:531
ExportAcadoFunction rhs3
uint getNX1() const
Definition: model_data.cpp:489
IntegratorExport(UserInteraction *_userInteraction=0, const std::string &_commonHeaderName="")
Base class for all variables within the symbolic expressions family.
Definition: expression.hpp:56
Allows to export automatically generated algorithms for fast model predictive control.
returnValue getNameDiffsOutputs(std::vector< std::string > &names) const
Definition: model_data.cpp:655
const std::string getNameRhs() const
Definition: model_data.cpp:629
const std::string getNameDiffsOutput() const
Definition: model_data.cpp:644
ExportVariable rk_eta
ExportAcadoFunction diffs_rhs3
const std::string getNameDiffsRhs() const
Definition: model_data.cpp:634
uint getN() const
Definition: model_data.cpp:557
uint getNDX() const
Definition: model_data.cpp:507
std::vector< Expression > outputExpressions
const std::string getNameOutputRHS() const
int acadoRoundAway(double x)
returnValue getIntegrationGrid(Grid &integrationGrid_) const
Definition: model_data.cpp:389
unsigned getDim() const
Definition: vector.hpp:172
int getDim() const
uint getNU() const
Definition: model_data.cpp:540
returnValue getOutputGrids(std::vector< Grid > &outputGrids_) const
Definition: model_data.cpp:196
const std::string getNameRHS() const
virtual returnValue propagateOutputSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &index3, const ExportIndex &tmp_index)
ExportVariable reset_int
virtual returnValue setLinearInput(const DMatrix &M1, const DMatrix &A1, const DMatrix &B1)
BooleanType hasOutputs() const
Definition: model_data.cpp:145
Encapsulates all user interaction for setting options, logging data and plotting results.
virtual returnValue propagateInputSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &index3, const ExportIndex &tmp_index)
returnValue addStatement(const ExportStatement &_statement)
virtual returnValue updateInputSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &tmp_index)
ExportFunction integrate
ExportFunction fullRhs
BooleanType hasCompressedStorage() const
Definition: model_data.cpp:471
unsigned getNumRows() const
Definition: matrix.hpp:185
virtual returnValue copy(const IntegratorExport &arg)
std::vector< uint > num_outputs
uint getDimOUTPUT(uint index) const
uint getNXA() const
Definition: model_data.cpp:525
Allows to export a tailored integrator for fast model predictive control.
ExportVariable rk_diffsNew2
unsigned getNumCols() const
Definition: matrix.hpp:189
uint getNumIntervals() const
returnValue getNumSteps(DVector &_numSteps) const
Definition: model_data.cpp:152
virtual returnValue setModelData(const ModelData &data)
returnValue getNARXmodel(uint &_delay, DMatrix &_parms) const
Definition: model_data.cpp:210
GenericVector< T > sumRow() const
Definition: matrix.cpp:114
returnValue getLinearInput(DMatrix &M1_, DMatrix &A1_, DMatrix &B1_) const
Definition: model_data.cpp:219
DifferentialStateDerivative dx
int getNX() const
Definition: function.cpp:207
std::string getName() const
virtual returnValue getGrid(Grid &grid_) const
ExportAcadoFunction lin_input
double getLastTime() const
virtual returnValue getOutputGrids(std::vector< Grid > &outputGrids_) const
uint getNX() const
Definition: model_data.cpp:478
#define BEGIN_NAMESPACE_ACADO
virtual const std::string getNameFullRHS() const
ExportVariable error_code
returnValue clearStaticCounters()
Definition: expression.hpp:398
uint getNDX3() const
Definition: model_data.cpp:516
const std::string getNameOutput() const
Definition: model_data.cpp:639
virtual returnValue setupOutput(const std::vector< Grid > outputGrids_, const std::vector< Expression > rhs)=0
IntegratorExport & operator=(const IntegratorExport &arg)
ExportVariable rk_diffsNew1
returnValue getNameOutputs(std::vector< std::string > &names) const
Definition: model_data.cpp:649
virtual returnValue setup()=0
uint getNOD() const
Definition: model_data.cpp:551
virtual returnValue setDifferentialEquation(const Expression &rhs)=0
uint getNX3() const
Definition: model_data.cpp:501
uint getNP() const
Definition: model_data.cpp:546
virtual returnValue clear()
BooleanType exportRhs() const
Definition: model_data.cpp:465
Allows to export code for a block of statements.
virtual returnValue getOutputExpressions(std::vector< Expression > &outputExpressions_) const
virtual returnValue updateOutputSystem(ExportStatementBlock *block, const ExportIndex &index1, const ExportIndex &index2, const ExportIndex &tmp_index)
ExportVariable getCol(const ExportIndex &idx) const
returnValue init(const Function &_f, const std::string &_name="acadoFcn", const uint _numX=0, const uint _numXA=0, const uint _numU=0, const uint _numP=0, const uint _numDX=0, const uint _numOD=0)
uint getNX2() const
Definition: model_data.cpp:495
#define ACADOERROR(retval)
virtual bool equidistantControlGrid() const
Defines a matrix-valued variable to be used for exporting code.
ExportAcadoFunction rhs
#define ACADOERRORTEXT(retval, text)
Allows to setup and evaluate differential equations (ODEs and DAEs) based on SymbolicExpressions.
uint getDim() const


acado
Author(s): Milan Vukov, Rien Quirynen
autogenerated on Mon Jun 10 2019 12:34:42