Tempus  Version of the Day
Time Integration
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Tempus_UnitTest_BDF2.cpp
Go to the documentation of this file.
1 // @HEADER
2 // ****************************************************************************
3 // Tempus: Copyright (2017) Sandia Corporation
4 //
5 // Distributed under BSD 3-clause license (See accompanying file Copyright.txt)
6 // ****************************************************************************
7 // @HEADER
8 
9 #include <fstream>
10 #include <vector>
11 
14 #include "Teuchos_TimeMonitor.hpp"
15 #include "Teuchos_DefaultComm.hpp"
16 
17 #include "Thyra_VectorStdOps.hpp"
18 
19 #include "Tempus_IntegratorBasic.hpp"
21 
22 #include "Tempus_StepperBDF2.hpp"
27 
28 #include "../TestModels/SinCosModel.hpp"
29 #include "../TestModels/VanDerPolModel.hpp"
30 #include "../TestUtils/Tempus_ConvergenceTestUtils.hpp"
31 
32 
33 namespace Tempus_Unit_Test {
34 
35  using Teuchos::RCP;
36  using Teuchos::rcp;
37  using Teuchos::rcp_const_cast;
38  using Teuchos::rcp_dynamic_cast;
40  using Teuchos::sublist;
41  using Teuchos::getParametersFromXmlFile;
42 
43 
44  // Comment out any of the following tests to exclude from build/run.
45 
46 
47  // ************************************************************
48  // ************************************************************
49  TEUCHOS_UNIT_TEST(BDF2, Default_Construction)
50  {
51  auto model = rcp(new Tempus_Test::SinCosModel<double>());
52 
53  // Default construction.
54  auto stepper = rcp(new Tempus::StepperBDF2<double>());
55  stepper->setModel(model);
56  stepper->initialize();
57  TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
58 
59 
60  // Default values for construction.
61  auto modifier = rcp(new Tempus::StepperBDF2ModifierDefault<double>());
62  auto solver = rcp(new Thyra::NOXNonlinearSolver());
63  solver->setParameterList(Tempus::defaultSolverParameters());
64 
65  auto startUpStepper = rcp(new Tempus::StepperDIRK_1StageTheta<double>());
66  startUpStepper->setModel(model); // Can use the same model since both steppers are implicit ODEs.
67  startUpStepper->initialize();
68 
69  auto defaultStepper = rcp(new Tempus::StepperBDF2<double>());
70  bool useFSAL = defaultStepper->getUseFSAL();
71  std::string ICConsistency = defaultStepper->getICConsistency();
72  bool ICConsistencyCheck = defaultStepper->getICConsistencyCheck();
73  bool zeroInitialGuess = defaultStepper->getZeroInitialGuess();
74 
75  // Test the set functions.
76  stepper->setAppAction(modifier); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
77  stepper->setSolver(solver); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
78  stepper->setStartUpStepper(startUpStepper); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
79  stepper->setUseFSAL(useFSAL); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
80  stepper->setICConsistency(ICConsistency); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
81  stepper->setICConsistencyCheck(ICConsistencyCheck); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
82  stepper->setZeroInitialGuess(zeroInitialGuess); stepper->initialize(); TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
83 
84  stepper = rcp(new Tempus::StepperBDF2<double>(model, solver, startUpStepper, useFSAL,
85  ICConsistency, ICConsistencyCheck, zeroInitialGuess,modifier));
86  TEUCHOS_TEST_FOR_EXCEPT(!stepper->isInitialized());
87  // Test stepper properties.
88  TEUCHOS_ASSERT(stepper->getOrder() == 2);
89  }
90 
91 
92  // ************************************************************
93  // ************************************************************
94  TEUCHOS_UNIT_TEST(BDF2, StepperFactory_Construction)
95  {
96  auto model = rcp(new Tempus_Test::SinCosModel<double>());
97  testFactoryConstruction("BDF2", model);
98  }
99 
100 
101  // ************************************************************
102  // ************************************************************
103 class StepperBDF2ModifierTest
104  : virtual public Tempus::StepperBDF2ModifierBase<double>
105 {
106 public:
107 
109  StepperBDF2ModifierTest()
110  : testBEGIN_STEP(false),testBEFORE_SOLVE(false),
111  testAFTER_SOLVE(false),testEND_STEP(false),
112  testCurrentValue(-0.99), testWorkingValue(-0.99),
113  testDt(.99), testType("")
114  {}
115 
117  virtual ~StepperBDF2ModifierTest(){}
118 
120  virtual void modify(Teuchos::RCP<Tempus::SolutionHistory<double> > sh,
123  {
124  switch(actLoc) {
126  {
127  testBEGIN_STEP = true;
128  auto x = sh->getWorkingState()->getX();
129  testCurrentValue = get_ele(*(x), 0);
130  break;
131  }
133  {
134  testBEFORE_SOLVE = true;
135  testType = "BDF2 - Modifier";
136  break;
137  }
139  {
140  testAFTER_SOLVE = true;
141  testDt = sh->getCurrentState()->getTimeStep()/10.0;
142  sh->getCurrentState()->setTimeStep(testDt);
143  break;
144  }
146  {
147  testEND_STEP = true;
148  auto x = sh->getWorkingState()->getX();
149  testWorkingValue = get_ele(*(x), 0);
150  break;
151  }
152  default:
153  TEUCHOS_TEST_FOR_EXCEPTION(true, std::logic_error,
154  "Error - unknown action location.\n");
155  }
156  }
157  bool testBEGIN_STEP;
158  bool testBEFORE_SOLVE;
159  bool testAFTER_SOLVE;
160  bool testEND_STEP;
161  double testCurrentValue;
162  double testWorkingValue;
163  double testDt;
164  std::string testType;
165 };
166 
167 TEUCHOS_UNIT_TEST(BDF2, AppAction_Modifier)
168 {
169  auto model = rcp(new Tempus_Test::SinCosModel<double>());
170 
171  // Setup Stepper for field solve ----------------------------
172  auto stepper = rcp(new Tempus::StepperBDF2<double>());
173  stepper->setModel(model);
174  auto modifier = rcp(new StepperBDF2ModifierTest());
175  stepper->setAppAction(modifier);
176  stepper->initialize();
177 
178  // Setup initial condition SolutionState --------------------
179  auto inArgsIC = model->getNominalValues();
180  auto icSolution =
181  rcp_const_cast<Thyra::VectorBase<double> > (inArgsIC.get_x());
182  auto icState = Tempus::createSolutionStateX(icSolution);
183  icState->setTime (0.0);
184  icState->setIndex (0);
185  icState->setTimeStep(1.0);
186  icState->setOrder (stepper->getOrder());
187  icState->setSolutionStatus(Tempus::Status::PASSED); // ICs are passing.
188 
189  // Setup TimeStepControl ------------------------------------
190  auto timeStepControl = rcp(new Tempus::TimeStepControl<double>());
191  timeStepControl->setInitIndex(0);
192  timeStepControl->setInitTime (0.0);
193  timeStepControl->setFinalTime(2.0);
194  timeStepControl->setInitTimeStep(1.0);
195  timeStepControl->initialize();
196 
197  // Setup SolutionHistory ------------------------------------
198  auto solutionHistory = rcp(new Tempus::SolutionHistory<double>());
199  solutionHistory->setName("Forward States");
200  solutionHistory->setStorageType(Tempus::STORAGE_TYPE_STATIC);
201  solutionHistory->setStorageLimit(3);
202  solutionHistory->addState(icState);
203 
204  // Take two time steps (the first step will not test BDF2's modifier)
205  stepper->setInitialConditions(solutionHistory);
206  solutionHistory->initWorkingState();
207  double dt = 1.0;
208  solutionHistory->getWorkingState()->setTimeStep(dt);
209  stepper->takeStep(solutionHistory);
210  solutionHistory->promoteWorkingState();
211  solutionHistory->initWorkingState();
212  stepper->takeStep(solutionHistory);
213 
214  TEST_COMPARE(modifier->testBEGIN_STEP, ==, true);
215  TEST_COMPARE(modifier->testBEFORE_SOLVE, ==, true);
216  TEST_COMPARE(modifier->testAFTER_SOLVE, ==, true);
217  TEST_COMPARE(modifier->testEND_STEP, ==, true);
218 
219  auto Dt = solutionHistory->getCurrentState()->getTimeStep();
220  TEST_FLOATING_EQUALITY(modifier->testDt, Dt, 1.0e-15);
221  auto x = solutionHistory->getCurrentState()->getX();
222  TEST_FLOATING_EQUALITY(modifier->testCurrentValue, get_ele(*(x), 0), 1.0e-15);
223  x = solutionHistory->getWorkingState()->getX();
224  TEST_FLOATING_EQUALITY(modifier->testWorkingValue, get_ele(*(x), 0), 1.0e-15);
225  TEST_COMPARE(modifier->testType, ==, "BDF2 - Modifier");
226  }
227 
228  // ************************************************************
229  // ************************************************************
230 class StepperBDF2ObserverTest
231  : virtual public Tempus::StepperBDF2ObserverBase<double>
232 {
233 public:
234 
236  StepperBDF2ObserverTest()
237  : testBEGIN_STEP(false),testBEFORE_SOLVE(false),
238  testAFTER_SOLVE(false),testEND_STEP(false),
239  testCurrentValue(0.99), testWorkingValue(0.99),
240  testDt(.99), testType("")
241  {}
242 
244  virtual ~StepperBDF2ObserverTest(){}
245 
247  virtual void modify(Teuchos::RCP<Tempus::SolutionHistory<double> > sh,
250  {
251  switch(actLoc) {
253  {
254  testBEGIN_STEP = true;
255  auto x = sh->getCurrentState()->getX();
256  testCurrentValue = get_ele(*(x), 0);
257  break;
258  }
260  {
261  testBEFORE_SOLVE = true;
262  testType = stepper->getStepperType();
263  break;
264  }
266  {
267  testAFTER_SOLVE = true;
268  testDt = sh->getCurrentState()->getTimeStep();
269  break;
270  }
272  {
273  testEND_STEP = true;
274  auto x = sh->getWorkingState()->getX();
275  testWorkingValue = get_ele(*(x), 0);
276  break;
277  }
278 
279  default:
280  TEUCHOS_TEST_FOR_EXCEPTION(true, std::logic_error,
281  "Error - unknown action location.\n");
282  }
283  }
284  bool testBEGIN_STEP;
285  bool testBEFORE_SOLVE;
286  bool testAFTER_SOLVE;
287  bool testEND_STEP;
288  double testCurrentValue;
289  double testWorkingValue;
290  double testDt;
291  std::string testType;
292 };
293 
294 TEUCHOS_UNIT_TEST(BDF2, AppAction_Observer)
295 {
296  auto model = rcp(new Tempus_Test::SinCosModel<double>());
297 
298  // Setup Stepper for field solve ----------------------------
299  auto stepper = rcp(new Tempus::StepperBDF2<double>());
300  stepper->setModel(model);
301  auto observer = rcp(new StepperBDF2ModifierTest());
302  stepper->setAppAction(observer);
303  stepper->initialize();
304 
305  // Setup initial condition SolutionState --------------------
306  auto inArgsIC = model->getNominalValues();
307  auto icSolution =
308  rcp_const_cast<Thyra::VectorBase<double> > (inArgsIC.get_x());
309  auto icState = Tempus::createSolutionStateX(icSolution);
310  icState->setTime (0.0);
311  icState->setIndex (0);
312  icState->setTimeStep(1.0);
313  icState->setOrder (stepper->getOrder());
314  icState->setSolutionStatus(Tempus::Status::PASSED); // ICs are passing.
315 
316  // Setup TimeStepControl ------------------------------------
317  auto timeStepControl = rcp(new Tempus::TimeStepControl<double>());
318  timeStepControl->setInitIndex(0);
319  timeStepControl->setInitTime (0.0);
320  timeStepControl->setFinalTime(2.0);
321  timeStepControl->setInitTimeStep(1.0);
322  timeStepControl->initialize();
323 
324  // Setup SolutionHistory ------------------------------------
325  auto solutionHistory = rcp(new Tempus::SolutionHistory<double>());
326  solutionHistory->setName("Forward States");
327  solutionHistory->setStorageType(Tempus::STORAGE_TYPE_STATIC);
328  solutionHistory->setStorageLimit(3);
329  solutionHistory->addState(icState);
330 
331  // Take two time steps (the first step will not test BDF2's modifier)
332  stepper->setInitialConditions(solutionHistory);
333  solutionHistory->initWorkingState();
334  double dt = 1.0;
335  solutionHistory->getWorkingState()->setTimeStep(dt);
336  stepper->takeStep(solutionHistory);
337  solutionHistory->promoteWorkingState();
338  solutionHistory->initWorkingState();
339  stepper->takeStep(solutionHistory);
340 
341  TEST_COMPARE(observer->testBEGIN_STEP, ==, true);
342  TEST_COMPARE(observer->testBEFORE_SOLVE, ==, true);
343  TEST_COMPARE(observer->testAFTER_SOLVE, ==, true);
344  TEST_COMPARE(observer->testEND_STEP, ==, true);
345 
346  auto Dt = solutionHistory->getCurrentState()->getTimeStep();
347  TEST_FLOATING_EQUALITY(observer->testDt, Dt, 1.0e-15);
348 
349  auto x = solutionHistory->getCurrentState()->getX();
350  TEST_FLOATING_EQUALITY(observer->testCurrentValue, get_ele(*(x), 0), 1.0e-15);
351  x = solutionHistory->getWorkingState()->getX();
352  TEST_FLOATING_EQUALITY(observer->testWorkingValue, get_ele(*(x), 0), 1.0e-15);
353  TEST_COMPARE(observer->testType, ==, "BDF2 - Modifier");
354 }
355 
356 
357 class StepperBDF2ModifierXTest
358  : virtual public Tempus::StepperBDF2ModifierXBase<double>
359 {
360 public:
361 
363  StepperBDF2ModifierXTest()
364  : testX_BEGIN_STEP(false),testX_BEFORE_SOLVE(false),
365  testX_AFTER_SOLVE(false),testX_END_STEP(false),
366  testXbegin(-.99),testXend(-.99),testTime(0.0),testDt(0.0)
367  {}
368 
370  virtual ~StepperBDF2ModifierXTest(){}
371 
373  virtual void modify(
375  const double time, const double dt,
377  {
378  switch(modType) {
380  {
381  testX_BEGIN_STEP = true;
382  testXbegin = get_ele(*(x), 0);
383  break;
384  }
386  {
387  testX_BEFORE_SOLVE = true;
388  testDt = dt;
389  break;
390  }
392  {
393  testX_AFTER_SOLVE = true;
394  testTime = time;
395  break;
396  }
398  {
399  testX_END_STEP = true;
400  testXend = get_ele(*(x), 0);
401  break;
402  }
403  default:
404  TEUCHOS_TEST_FOR_EXCEPTION(true, std::logic_error,
405  "Error - unknown action location.\n");
406  }
407  }
408  bool testX_BEGIN_STEP;
409  bool testX_BEFORE_SOLVE;
410  bool testX_AFTER_SOLVE;
411  bool testX_END_STEP;
412  double testXbegin;
413  double testXend;
414  double testTime;
415  double testDt;
416 };
417 
418 TEUCHOS_UNIT_TEST(BDF2, AppAction_ModifierX)
419 {
420  auto model = rcp(new Tempus_Test::SinCosModel<double>());
421  // Setup Stepper for field solve ----------------------------
422  auto stepper = rcp(new Tempus::StepperBDF2<double>());
423  stepper->setModel(model);
424  auto modifierX = rcp(new StepperBDF2ModifierXTest());
425  stepper->setAppAction(modifierX);
426  stepper->initialize();
427 
428  // Setup initial condition SolutionState --------------------
429  auto inArgsIC = model->getNominalValues();
430  auto icSolution =
431  rcp_const_cast<Thyra::VectorBase<double> > (inArgsIC.get_x());
432  auto icState = Tempus::createSolutionStateX(icSolution);
433  icState->setTime (0.0);
434  icState->setIndex (0);
435  icState->setTimeStep(1.0);
436  icState->setOrder (stepper->getOrder());
437  icState->setSolutionStatus(Tempus::Status::PASSED); // ICs are passing.
438 
439  // Setup TimeStepControl ------------------------------------
440  auto timeStepControl = rcp(new Tempus::TimeStepControl<double>());
441  timeStepControl->setInitIndex(0);
442  timeStepControl->setInitTime (0.0);
443  timeStepControl->setFinalTime(2.0);
444  timeStepControl->setInitTimeStep(1.0);
445  timeStepControl->initialize();
446 
447  // Setup SolutionHistory ------------------------------------
448  auto solutionHistory = rcp(new Tempus::SolutionHistory<double>());
449  solutionHistory->setName("Forward States");
450  solutionHistory->setStorageType(Tempus::STORAGE_TYPE_STATIC);
451  solutionHistory->setStorageLimit(3);
452  solutionHistory->addState(icState);
453 
454 
455  // Take two time steps (the first step will not test BDF2's modifier)
456  stepper->setInitialConditions(solutionHistory);
457  solutionHistory->initWorkingState();
458  double dt = 1.0;
459  solutionHistory->getWorkingState()->setTimeStep(dt);
460  stepper->takeStep(solutionHistory);
461  solutionHistory->promoteWorkingState();
462  solutionHistory->initWorkingState();
463  stepper->takeStep(solutionHistory);
464 
465  TEST_COMPARE(modifierX->testX_BEGIN_STEP, ==, true);
466  TEST_COMPARE(modifierX->testX_BEFORE_SOLVE, ==, true);
467  TEST_COMPARE(modifierX->testX_AFTER_SOLVE, ==, true);
468  TEST_COMPARE(modifierX->testX_END_STEP, ==, true);
469 
470  // Testing that values can be set through the Modifier.
471  auto x = solutionHistory->getCurrentState()->getX();
472  TEST_FLOATING_EQUALITY(modifierX->testXbegin, get_ele(*(x), 0), 1.0e-15);
473  auto Dt = solutionHistory->getWorkingState()->getTimeStep();
474  x = solutionHistory->getWorkingState()->getX();
475  TEST_FLOATING_EQUALITY(modifierX->testXend, get_ele(*(x), 0), 1.0e-15);
476  TEST_FLOATING_EQUALITY(modifierX->testDt, Dt, 1.0e-15);
477  auto time = solutionHistory->getWorkingState()->getTime();
478  TEST_FLOATING_EQUALITY(modifierX->testTime, time, 1.0e-15);
479  }
480 
481 } // namespace Tempus_Test
BDF2 (Backward-Difference-Formula-2) time stepper.
Teuchos::RCP< SolutionState< Scalar > > createSolutionStateX(const Teuchos::RCP< Thyra::VectorBase< Scalar > > &x, const Teuchos::RCP< Thyra::VectorBase< Scalar > > &xdot=Teuchos::null, const Teuchos::RCP< Thyra::VectorBase< Scalar > > &xdotdot=Teuchos::null)
Nonmember constructor from non-const solution vectors, x.
ACTION_LOCATION
Indicates the location of application action (see algorithm).
void testFactoryConstruction(std::string stepperType, const Teuchos::RCP< const Thyra::ModelEvaluator< double > > &model)
Unit test utility for Stepper construction through StepperFactory.
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
#define TEST_COMPARE(v1, comp, v2)
#define TEST_FLOATING_EQUALITY(v1, v2, tol)
Sine-Cosine model problem from Rythmos. This is a canonical Sine-Cosine differential equation with a...
Teuchos::RCP< Teuchos::ParameterList > defaultSolverParameters()
Returns the default solver ParameterList for implicit Steppers.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
virtual void modify(Teuchos::RCP< Thyra::VectorBase< double > >, const double, const double, const MODIFIER_TYPE modType)=0
Modify solution based on the MODIFIER_TYPE.
TEUCHOS_UNIT_TEST(BackwardEuler, Default_Construction)
TimeStepControl manages the time step size. There several mechanisms that effect the time step size a...
SolutionHistory is basically a container of SolutionStates. SolutionHistory maintains a collection of...
Keep a fix number of states.
#define TEUCHOS_ASSERT(assertion_test)
MODIFIER_TYPE
Indicates the location of application action (see algorithm).
#define TEUCHOS_TEST_FOR_EXCEPT(throw_exception_test)