Tempus  Version of the Day
Time Integration
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Tempus_SolutionHistory_impl.hpp
Go to the documentation of this file.
1 //@HEADER
2 // *****************************************************************************
3 // Tempus: Time Integration and Sensitivity Analysis Package
4 //
5 // Copyright 2017 NTESS and the Tempus contributors.
6 // SPDX-License-Identifier: BSD-3-Clause
7 // *****************************************************************************
8 //@HEADER
9 
10 #ifndef Tempus_SolutionHistory_impl_hpp
11 #define Tempus_SolutionHistory_impl_hpp
12 
13 #include "Teuchos_StandardParameterEntryValidators.hpp"
14 #include "Teuchos_TimeMonitor.hpp"
15 
16 #include "Thyra_VectorStdOps.hpp"
17 
20 
21 namespace Tempus {
22 
23 template <class Scalar>
25  : name_("Solution History"), storageType_(STORAGE_TYPE_UNDO), storageLimit_(2)
26 {
27  using Teuchos::RCP;
28  // Create history, a vector of solution states.
29  history_ = rcp(new std::vector<RCP<SolutionState<Scalar> > >);
31  isInitialized_ = false;
32 }
33 
34 template <class Scalar>
36  std::string name,
37  Teuchos::RCP<std::vector<Teuchos::RCP<SolutionState<Scalar> > > > history,
38  Teuchos::RCP<Interpolator<Scalar> > interpolator, StorageType storageType,
39  int storageLimit)
40 {
41  setName(name);
42  setHistory(history);
43  setInterpolator(interpolator);
44  setStorageType(storageType);
45  setStorageLimit(storageLimit);
46 
47  isInitialized_ = false;
48  if (getNumStates() > 0) isInitialized_ = true;
49 }
50 
51 template <class Scalar>
53  const Teuchos::RCP<SolutionState<Scalar> >& state, bool doChecks)
54 {
55  // Check that we're not going to exceed our storage limit:
56  if (Teuchos::as<int>(history_->size() + 1) > storageLimit_) {
57  switch (storageType_) {
58  case STORAGE_TYPE_INVALID: {
60  true, std::logic_error,
61  "Error - Storage type is STORAGE_TYPE_INVALID.\n");
62  break;
63  }
66  case STORAGE_TYPE_UNDO: {
67  if (state->getTime() >= history_->front()->getTime()) {
68  // Case: State is younger than the oldest state in history.
69  // Remove state from the beginning of history, then add new state.
70  history_->erase(history_->begin());
71  }
72  else {
73  // Case: State is older than the oldest state in history.
74  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
75  Teuchos::OSTab ostab(out, 1, "SolutionHistory::addState");
76  *out << "Warning, state is older than oldest state in history. "
77  << "State not added!" << std::endl;
78  return;
79  }
80  break;
81  }
82  case STORAGE_TYPE_UNLIMITED: break;
83  default:
84  TEUCHOS_TEST_FOR_EXCEPTION(true, std::logic_error,
85  "Error - unknown storage type.\n");
86  }
87  }
88 
89  // Add new state in chronological order.
90  if (history_->size() == 0) {
91  history_->push_back(state);
92  }
93  else {
94  typename std::vector<Teuchos::RCP<SolutionState<Scalar> > >::iterator
95  state_it = history_->begin();
96  bool equal = false;
97  const Scalar newTime = state->getTime();
98  for (; state_it < history_->end(); state_it++) {
99  const Scalar shTime = (*state_it)->getTime();
100  if (doChecks) {
101  const Scalar denom = std::max(std::fabs(shTime), std::fabs(newTime));
102  if (std::fabs(newTime - shTime) < 1.0e-14 * denom) {
103  equal = true;
104  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
105  Teuchos::OSTab ostab(out, 1, "SolutionHistory::addState");
106  *out << "Warning, state to be added matches state in history. "
107  << "State not added!" << std::endl;
108 
109  *out << "===============" << std::endl;
110  *out << "Added SolutionState -- ";
111  (*state_it)->describe(*out, Teuchos::VERB_MEDIUM);
112  *out << "===============" << std::endl;
113  this->describe(*out, Teuchos::VERB_MEDIUM);
114 
115  std::exit(-1);
116  break;
117  }
118  }
119  if (newTime < shTime) break;
120  }
121  if (!equal) history_->insert(state_it, state);
122  }
123 
125  getNumStates() <= 0, std::logic_error,
126  "Error - SolutionHistory::addState() Invalid history size!\n");
127 
128  return;
129 }
130 
131 template <class Scalar>
133  const Teuchos::RCP<SolutionState<Scalar> >& state, const bool updateTime)
134 {
135  using Teuchos::RCP;
136 
137  auto cs = getCurrentState();
138  state->setSolutionStatus(Status::WORKING);
139  state->setIndex(cs->getIndex() + 1);
140  if (updateTime) {
141  state->setTime(cs->getTime() + cs->getTimeStep());
142  state->setTimeStep(cs->getTimeStep());
143  }
144 
145  addState(state);
146  workingState_ = (*history_)[getNumStates() - 1];
147 }
148 
149 template <class Scalar>
151  const Teuchos::RCP<SolutionState<Scalar> >& state)
152 {
153  if (history_->size() != 0) {
154  auto state_it = history_->rbegin();
155  for (; state_it < history_->rend(); state_it++) {
156  if (state->getTime() == (*state_it)->getTime()) break;
157  }
158 
159  TEUCHOS_TEST_FOR_EXCEPTION(state_it == history_->rend(), std::logic_error,
160  "Error - removeState() Could not remove state = "
161  << (*state_it)->description());
162 
163  // Need to be careful when erasing a reverse iterator.
164  history_->erase(std::next(state_it).base());
165  }
166  return;
167 }
168 
169 template <class Scalar>
171 {
172  Teuchos::RCP<SolutionState<Scalar> > tmpState = findState(time);
173  removeState(tmpState);
174 }
175 
176 template <class Scalar>
178  const Scalar time) const
179 {
180  // Use last step in solution history as the scale for comparing times
181  Scalar scale = 1.0;
182  if (history_->size() > 0)
183  scale = (*history_)[history_->size() - 1]->getTime();
184  if (approxZero(scale)) scale = Scalar(1.0);
185 
186  const Scalar absTol = scale * numericalTol<Scalar>();
188  !(minTime() - absTol <= time && time <= maxTime() + absTol),
189  std::logic_error,
190  "Error - SolutionHistory::findState() Requested time out of range!\n"
191  << " [Min, Max] = ["
192  << minTime() << ", " << maxTime()
193  << "]\n time = "
194  << time << "\n");
195 
196  // Linear search
197  auto state_it = history_->begin();
198  for (; state_it < history_->end(); ++state_it) {
199  if (approxEqualAbsTol(time, (*state_it)->getTime(), absTol)) break;
200  }
201 
202  TEUCHOS_TEST_FOR_EXCEPTION(state_it == history_->end(), std::logic_error,
203  "Error - SolutionHistory::findState()!\n"
204  " Did not find a SolutionState with time = "
205  << time << std::endl);
206 
207  return *state_it;
208 }
209 
210 template <class Scalar>
212  const Scalar time) const
213 {
214  Teuchos::RCP<SolutionState<Scalar> > state_out = getCurrentState()->clone();
215  interpolate<Scalar>(*interpolator_, history_, time, state_out.get());
216  return state_out;
217 }
218 
219 template <class Scalar>
221  const Scalar time, SolutionState<Scalar>* state_out) const
222 {
223  interpolate<Scalar>(*interpolator_, history_, time, state_out);
224 }
225 
227 template <class Scalar>
229 {
230  TEMPUS_FUNC_TIME_MONITOR("Tempus::SolutionHistory::initWorkingState()");
231  {
233  getCurrentState() == Teuchos::null, std::logic_error,
234  "Error - SolutionHistory::initWorkingState()\n"
235  "Can not initialize working state without a current state!\n");
236 
237  // If workingState_ has a valid pointer, we are still working on it,
238  // i.e., step failed and trying again. There are a couple options:
239  // 1. Reuse the workingState as it might be a good guess. This
240  // could help with performance. This was the initial implementation.
241  // 2. Reset the workingState to the last time step. This could
242  // be more robust in the case of the workingState failing with nans.
243  // This is the current implementation.
244  if (getWorkingState(false) != Teuchos::null) {
245  Thyra::V_V(getWorkingState()->getX().ptr(), *(getCurrentState()->getX()));
246  return;
247  }
248 
250  if (getNumStates() < storageLimit_) {
251  // Create newState which is duplicate of currentState
252  newState = getCurrentState()->clone();
253  }
254  else {
255  // Recycle old state and copy currentState
256  newState = (*history_)[0];
257  history_->erase(history_->begin());
258  if (getNumStates() > 0) newState->copy(getCurrentState());
259  // When using the Griewank algorithm, we will want to select which
260  // older state to recycle.
261  }
262 
263  addWorkingState(newState);
264  }
265  return;
266 }
267 
268 template <class Scalar>
270 {
271  auto ws = getWorkingState();
272 
273  if (ws->getSolutionStatus() == Status::PASSED) {
274  ws->setNFailures(std::max(0, ws->getNFailures() - 1));
275  ws->setNConsecutiveFailures(0);
276  ws->setSolutionStatus(Status::PASSED);
277  // ws->setIsSynced(true);
278  ws->setIsInterpolated(false);
279  workingState_ = Teuchos::null;
280  }
281  else {
282  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
283  Teuchos::OSTab ostab(out, 1, "SolutionHistory::promoteWorkingState()");
284  *out << "Warning - WorkingState is not passing, so not promoted!\n"
285  << std::endl;
286  }
287 }
288 
289 template <class Scalar>
292 {
293  this->setName(sh->getName());
294 
295  this->clear();
296  auto sh_history = sh->getHistory();
297  typename std::vector<Teuchos::RCP<SolutionState<Scalar> > >::iterator
298  state_it = sh_history->begin();
299  for (; state_it < sh_history->end(); state_it++) this->addState(*state_it);
300 
301  auto interpolator =
302  Teuchos::rcp_const_cast<Interpolator<Scalar> >(sh->getInterpolator());
303  this->setInterpolator(interpolator);
304 
305  this->setStorageType(sh->getStorageType());
306  this->setStorageLimit(sh->getStorageLimit());
307 }
308 
309 template <class Scalar>
311 {
312  storageLimit_ = std::max(1, storage_limit);
313 
314  if (storageType_ == STORAGE_TYPE_INVALID ||
315  storageType_ == STORAGE_TYPE_KEEP_NEWEST) {
316  if (storage_limit != 1) {
317  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
318  Teuchos::OSTab ostab(out, 1, "SolutionHistory::setStorageLimit");
319  *out << "Warning - 'Storage Limit' for 'Keep Newest' is 1.\n"
320  << " (Storage Limit = " << storage_limit << "). Resetting to 1."
321  << std::endl;
322  storageLimit_ = 1;
323  }
324  }
325  else if (storageType_ == STORAGE_TYPE_UNDO) {
326  if (storage_limit != 2) {
327  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
328  Teuchos::OSTab ostab(out, 1, "SolutionHistory::setStorageLimit");
329  *out << "Warning - 'Storage Limit' for 'Undo' is 2.\n"
330  << " (Storage Limit = " << storage_limit << "). Resetting to 2."
331  << std::endl;
332  storageLimit_ = 2;
333  }
334  }
335  else if (storageType_ == STORAGE_TYPE_STATIC) {
336  storageLimit_ = storage_limit;
337  }
338  else if (storageType_ == STORAGE_TYPE_UNLIMITED) {
339  storageLimit_ = std::numeric_limits<int>::max();
340  }
341 
343  (Teuchos::as<int>(history_->size()) > storageLimit_), std::logic_error,
344  "Error - requested storage limit = "
345  << storageLimit_
346  << " is smaller than the current number of states stored = "
347  << history_->size() << "!\n");
348 
349  isInitialized_ = false;
350 }
351 
352 template <class Scalar>
354 {
355  storageType_ = st;
356  if (storageType_ == STORAGE_TYPE_KEEP_NEWEST)
357  setStorageLimit(1);
358  else if (storageType_ == STORAGE_TYPE_UNDO)
359  setStorageLimit(2);
360  else if (storageType_ == STORAGE_TYPE_UNLIMITED)
361  setStorageLimit(std::numeric_limits<int>::max());
362  isInitialized_ = false;
363 }
364 
365 template <class Scalar>
367 {
368  if (s == "Keep Newest") { // Keep the single newest state
369  storageType_ = STORAGE_TYPE_KEEP_NEWEST;
370  storageLimit_ = 1;
371  }
372  else if (s == "Undo") { // Keep the 2 newest states for undo
373  storageType_ = STORAGE_TYPE_UNDO;
374  storageLimit_ = 2;
375  }
376  else if (s == "Static") { // Keep a fix number of states
377  storageType_ = STORAGE_TYPE_STATIC;
378  }
379  else if (s == "Unlimited") { // Grow the history as needed
380  storageType_ = STORAGE_TYPE_UNLIMITED;
381  }
382  else {
384  true, std::logic_error,
385  "Error - Unknown 'Storage Type' = '" << s << "'\n");
386  }
387  isInitialized_ = false;
388 }
389 
390 template <class Scalar>
392 {
393  std::string s = "Invalid";
394  if (storageType_ == STORAGE_TYPE_KEEP_NEWEST)
395  s = "Keep Newest";
396  else if (storageType_ == STORAGE_TYPE_UNDO)
397  s = "Undo";
398  else if (storageType_ == STORAGE_TYPE_STATIC)
399  s = "Static";
400  else if (storageType_ == STORAGE_TYPE_UNLIMITED)
401  s = "Unlimited";
402  return s;
403 }
404 
405 template <class Scalar>
408 {
409  Teuchos::RCP<SolutionState<Scalar> > state = Teuchos::null;
410  const int m = history_->size();
411  if (m < 1) {
412  if (warn) {
413  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
414  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndexN");
415  *out << "Warning - getStateTimeIndexN() No states in SolutionHistory!"
416  << std::endl;
417  }
418  }
419  else {
420  state = (*history_)[m - 1];
421  }
422  return state;
423 }
424 
425 template <class Scalar>
428 {
429  Teuchos::RCP<SolutionState<Scalar> > state = Teuchos::null;
430  const int m = history_->size();
431  if (m < 2) {
432  if (warn) {
433  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
434  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndexNM1");
435  *out << "Warning - getStateTimeIndexNM1() Not enough states in "
436  << "SolutionHistory! Size of history = " << getNumStates()
437  << std::endl;
438  }
439  }
440  else {
441  const int n = (*history_)[m - 1]->getIndex();
442  const int nm1 = (*history_)[m - 2]->getIndex();
443 
444  // No need to search SolutionHistory as states n and nm1 should be
445  // next to each other.
446  if (nm1 != n - 1) {
447  if (warn) {
448  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
449  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndexNM1");
450  *out << "Warning - getStateTimeIndexNM1() Timestep index n-1 is not in "
451  << "SolutionHistory!\n"
452  << " (n)th index = " << n << "\n"
453  << " (n-1)th index = " << nm1 << std::endl;
454  }
455  }
456  else {
457  state = (*history_)[m - 2];
458  }
459  }
460 
461  return state;
462 }
463 
464 template <class Scalar>
467 {
468  Teuchos::RCP<SolutionState<Scalar> > state = Teuchos::null;
469  const int m = history_->size();
470  if (m < 3) {
471  if (warn) {
472  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
473  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndexNM2");
474  *out << "Warning - getStateTimeIndexNM2() Not enough states in "
475  << "SolutionHistory! Size of history = " << getNumStates()
476  << std::endl;
477  }
478  }
479  else {
480  const int n = (*history_)[m - 1]->getIndex();
481  const int nm2 = (*history_)[m - 3]->getIndex();
482 
483  // Assume states n and nm2 are one away from each other.
484  if (nm2 != n - 2) {
485  // Check if it is at nm1
486  const int nm1 = (*history_)[m - 2]->getIndex();
487  if (nm1 == n - 2) {
488  state = (*history_)[m - 2];
489  }
490  else if (warn) {
491  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
492  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndexNM2");
493  *out << "Warning - getStateTimeIndexNM2() Timestep index n-2 is not in "
494  << "SolutionHistory!\n"
495  << " (n)th index = " << n << "\n"
496  << " (n-2)th index = " << nm2 << std::endl;
497  }
498  }
499  else {
500  state = (*history_)[m - 3];
501  }
502  }
503 
504  return state;
505 }
506 
507 template <class Scalar>
509  int index, bool warn) const
510 {
511  typename std::vector<Teuchos::RCP<SolutionState<Scalar> > >::iterator
512  state_it = history_->begin();
513  for (; state_it < history_->end(); state_it++) {
514  if ((*state_it)->getIndex() == index) break;
515  }
516 
517  Teuchos::RCP<SolutionState<Scalar> > state = Teuchos::null;
518  if (state_it == history_->end()) {
519  if (warn) {
520  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
521  Teuchos::OSTab ostab(out, 1, "SolutionHistory::getStateTimeIndex");
522  *out << "Warning - getStateTimeIndex() Timestep index is not in "
523  << "SolutionHistory!\n"
524  << " index = " << index << std::endl;
525  }
526  }
527  else {
528  state = *state_it;
529  }
530  return state;
531 }
532 
533 template <class Scalar>
535 {
536  return ("Tempus::SolutionHistory - '" + name_ + "'");
537 }
538 
539 template <class Scalar>
541  Teuchos::FancyOStream& out, const Teuchos::EVerbosityLevel verbLevel) const
542 {
543  auto l_out = Teuchos::fancyOStream(out.getOStream());
544  Teuchos::OSTab ostab(*l_out, 2, this->description());
545  l_out->setOutputToRootOnly(0);
546 
547  *l_out << "\n--- " << this->description() << " ---" << std::endl;
548 
549  if ((Teuchos::as<int>(verbLevel) ==
550  Teuchos::as<int>(Teuchos::VERB_DEFAULT)) ||
551  (Teuchos::as<int>(verbLevel) >= Teuchos::as<int>(Teuchos::VERB_LOW))) {
552  //*l_out << " interpolator = " << interpolator->description() <<
553  // std::endl;
554  *l_out << " storageLimit = " << storageLimit_ << std::endl;
555  *l_out << " storageType = " << getStorageTypeString() << std::endl;
556  *l_out << " number of states = " << history_->size() << std::endl;
557  if (history_->size() > 0) {
558  *l_out << " time range = (" << history_->front()->getTime() << ", "
559  << history_->back()->getTime() << ")" << std::endl;
560  }
561  }
562 
563  if (Teuchos::as<int>(verbLevel) >= Teuchos::as<int>(Teuchos::VERB_MEDIUM)) {
564  for (int i = 0; i < (int)history_->size(); ++i)
565  (*history_)[i]->describe(*l_out, verbLevel);
566  }
567  *l_out << std::string(this->description().length() + 8, '-') << std::endl;
568 }
569 
570 template <class Scalar>
573 {
575  Teuchos::parameterList("Solution History");
576 
577  pl->setName(getName());
578 
579  pl->set(
580  "Storage Type", getStorageTypeString(),
581  "'Storage Type' sets the memory storage. "
582  "'Keep Newest' - will retain the single newest solution state. "
583  "'Undo' - will retain two solution states in order to do a single undo. "
584  "'Static' - will retain 'Storage Limit' number of solution states. "
585  "'Unlimited' - will not remove any solution states!");
586 
587  pl->set(
588  "Storage Limit", getStorageLimit(),
589  "Limit on the number of SolutionStates that SolutionHistory can have.");
590 
591  pl->set("Interpolator", *interpolator_->getNonconstParameterList());
592 
593  return pl;
594 }
595 
596 template <class Scalar>
599 {
600  return Teuchos::rcp_const_cast<Teuchos::ParameterList>(getValidParameters());
601 }
602 
603 template <class Scalar>
605  const Teuchos::RCP<Interpolator<Scalar> >& interpolator)
606 {
607  if (interpolator == Teuchos::null) {
609  }
610  else {
611  interpolator_ = interpolator;
612  }
613  isInitialized_ = false;
614 }
615 
616 template <class Scalar>
619 {
620  return interpolator_;
621 }
622 
623 template <class Scalar>
626 {
627  return interpolator_;
628 }
629 
630 template <class Scalar>
632 {
633  Teuchos::RCP<Interpolator<Scalar> > old_interpolator = interpolator_;
634  interpolator_ = lagrangeInterpolator<Scalar>();
635  return old_interpolator;
636 }
637 
638 template <class Scalar>
639 void SolutionHistory<Scalar>::printHistory(std::string verb) const
640 {
641  Teuchos::RCP<Teuchos::FancyOStream> out = this->getOStream();
642  Teuchos::OSTab ostab(out, 1, "SolutionHistory::printHistory");
643  *out << name_ << " (size=" << history_->size() << ")"
644  << " (w - working; c - current; i - interpolated)" << std::endl;
645  for (int i = 0; i < (int)history_->size(); ++i) {
646  auto state = (*history_)[i];
647  *out << " ";
648  if (state == getWorkingState())
649  *out << "w - ";
650  else if (state == getCurrentState())
651  *out << "c - ";
652  else if (state->getIsInterpolated() == true)
653  *out << "i - ";
654  else
655  *out << " ";
656  *out << "[" << i << "] = " << state << std::endl;
657  if (verb == "medium" || verb == "high") {
658  if (state != Teuchos::null) {
659  auto x = state->getX();
660  *out << " x = " << x << std::endl
661  << " norm(x) = " << Thyra::norm(*x) << std::endl;
662  }
663  }
664  if (verb == "high") {
665  (*history_)[i]->describe(*out, this->getVerbLevel());
666  }
667  }
668 }
669 
670 template <class Scalar>
672 {
674  getNumStates() <= 0, std::logic_error,
675  "Error - SolutionHistory::initialize() Invalid history size!\n");
676 
678  interpolator_ == Teuchos::null, std::logic_error,
679  "Error - SolutionHistory::initialize() Interpolator is not set!\n");
680 
681  TEUCHOS_TEST_FOR_EXCEPTION(storageLimit_ < 1, std::logic_error,
682  "Error - SolutionHistory::initialize() Storage "
683  "Limit needs to a positive integer!\n"
684  << " Storage Limit = " << storageLimit_
685  << "\n");
686 
688  (storageType_ == STORAGE_TYPE_INVALID), std::logic_error,
689  "Error - SolutionHistory::initialize() Storage Type is invalid!\n");
690 
692  (storageType_ == STORAGE_TYPE_KEEP_NEWEST && storageLimit_ != 1),
693  std::logic_error,
694  "Error - SolutionHistory::initialize() \n"
695  << " For Storage Type = '" << getStorageTypeString()
696  << "', Storage Limit needs to be one.\n"
697  << " Storage Limit = " << storageLimit_ << "\n");
698 
700  (storageType_ == STORAGE_TYPE_UNDO && storageLimit_ != 2),
701  std::logic_error,
702  "Error - SolutionHistory::initialize() \n"
703  << " For Storage Type = '" << getStorageTypeString()
704  << "', Storage Limit needs to be two.\n"
705  << " Storage Limit = " << storageLimit_ << "\n");
706 
707  isInitialized_ = true; // Only place where this is set to true!
708 }
709 
710 // Nonmember constructors.
711 // ------------------------------------------------------------------------
712 
713 template <class Scalar>
715 {
716  auto sh = rcp(new SolutionHistory<Scalar>());
717  sh->setName("From createSolutionHistory");
718 
719  return sh;
720 }
721 
722 template <class Scalar>
725 {
726  auto sh = rcp(new SolutionHistory<Scalar>());
727  sh->setName("From createSolutionHistoryPL");
728 
729  if (pl == Teuchos::null || pl->numParams() == 0) return sh;
730 
731  pl->validateParametersAndSetDefaults(*sh->getValidParameters());
732 
733  sh->setName(pl->name());
734  sh->setStorageTypeString(pl->get("Storage Type", "Undo"));
735  sh->setStorageLimit(pl->get("Storage Limit", 2));
736 
738  Teuchos::sublist(pl, "Interpolator")));
739 
740  return sh;
741 }
742 
743 template <class Scalar>
745  const Teuchos::RCP<SolutionState<Scalar> >& state)
746 {
747  auto sh = rcp(new SolutionHistory<Scalar>());
748  sh->setName("From createSolutionHistoryState");
749  sh->addState(state);
750  return sh;
751 }
752 
753 template <class Scalar>
755  const Teuchos::RCP<const Thyra::ModelEvaluator<Scalar> >& model)
756 {
757  // Setup initial condition SolutionState --------------------
758  auto state = createSolutionStateME(model);
759  state->setTime(0.0);
760  state->setIndex(0);
761  state->setTimeStep(0.0);
762  state->setOrder(1);
763 
764  // Setup SolutionHistory ------------------------------------
765  auto sh = rcp(new SolutionHistory<Scalar>());
766  sh->setName("From createSolutionHistoryME");
767  sh->addState(state);
768 
769  return sh;
770 }
771 
772 } // namespace Tempus
773 #endif // Tempus_SolutionHistory_impl_hpp
Teuchos::RCP< Interpolator< Scalar > > unSetInterpolator()
Unset the interpolator for this history.
const std::string & name() const
Keep the 2 newest states for undo.
Teuchos::RCP< Interpolator< Scalar > > interpolator_
void initWorkingState()
Initialize the working state.
Teuchos::RCP< SolutionHistory< Scalar > > createSolutionHistory()
Nonmember constructor.
void printHistory(std::string verb="low") const
Print information on States in the SolutionHistory.
T & get(const std::string &name, T def_value)
Teuchos::RCP< SolutionState< Scalar > > interpolateState(const Scalar time) const
Generate and interpolate a new solution state at requested time.
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
Teuchos::RCP< Teuchos::ParameterList > getNonconstParameterList()
Return a valid non-const ParameterList with current settings.
T * get() const
Ordinal numParams() const
ParameterList & set(std::string const &name, T &&value, std::string const &docString="", RCP< const ParameterEntryValidator > const &validator=null)
Teuchos::RCP< Interpolator< Scalar > > getNonconstInterpolator()
void setStorageLimit(int storage_limit)
Set the maximum storage of this history.
Teuchos::RCP< SolutionHistory< Scalar > > createSolutionHistoryPL(Teuchos::RCP< Teuchos::ParameterList > pList)
Nonmember constructor from a ParameterList.
Teuchos::RCP< SolutionHistory< Scalar > > createSolutionHistoryME(const Teuchos::RCP< const Thyra::ModelEvaluator< Scalar > > &model)
Nonmember contructor from a Thyra ModelEvaluator.
Teuchos::RCP< SolutionState< Scalar > > getStateTimeIndex(int index, bool warn=true) const
Get the state with timestep index equal to &quot;index&quot;.
void initialize() const
Initialize SolutionHistory.
static Teuchos::RCP< Interpolator< Scalar > > createInterpolator(std::string interpolatorType="")
Create default interpolator from interpolator type (e.g., &quot;Linear&quot;).
void promoteWorkingState()
Promote the working state to current state.
void removeState(const Teuchos::RCP< SolutionState< Scalar > > &state)
Remove solution state.
bool isInitialized_
Bool if SolutionHistory is initialized.
Teuchos::RCP< SolutionState< Scalar > > getStateTimeIndexNM1(bool warn=true) const
Get the state with timestep index equal to n-1.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
Base strategy class for interpolation functionality.
virtual std::string description() const
Teuchos::RCP< SolutionState< Scalar > > getStateTimeIndexN(bool warn=true) const
Get the state with timestep index equal to n.
Teuchos::RCP< SolutionState< Scalar > > getStateTimeIndexNM2(bool warn=true) const
Get the state with timestep index equal to n-2.
void addState(const Teuchos::RCP< SolutionState< Scalar > > &state, bool doChecks=true)
Add solution state to history.
void validateParametersAndSetDefaults(ParameterList const &validParamList, int const depth=1000)
virtual void describe(Teuchos::FancyOStream &out, const Teuchos::EVerbosityLevel verbLevel) const
SolutionHistory is basically a container of SolutionStates. SolutionHistory maintains a collection of...
std::string getStorageTypeString() const
Set the string storage type.
Teuchos::RCP< SolutionState< Scalar > > createSolutionStateME(const Teuchos::RCP< const Thyra::ModelEvaluator< Scalar > > &model, const Teuchos::RCP< StepperState< Scalar > > &stepperState=Teuchos::null, const Teuchos::RCP< PhysicsState< Scalar > > &physicsState=Teuchos::null)
Nonmember constructor from Thyra ModelEvaluator.
void setStorageType(StorageType st)
Set the storage type via enum.
void addWorkingState(const Teuchos::RCP< SolutionState< Scalar > > &state, const bool updateTime=true)
Add a working solution state to history.
Keep a fix number of states.
Teuchos::RCP< SolutionHistory< Scalar > > createSolutionHistoryState(const Teuchos::RCP< SolutionState< Scalar > > &state)
Nonmember contructor from a SolutionState.
void setStorageTypeString(std::string st)
Set the storage type via string.
RCP< std::basic_ostream< char_type, traits_type > > getOStream()
bool approxEqualAbsTol(Scalar a, Scalar b, Scalar absTol)
Test if values are approximately equal within the absolute tolerance.
bool approxZero(Scalar value, Scalar tol=Teuchos::ScalarTraits< Scalar >::sfmin())
Test if value is approximately zero within tolerance.
Teuchos::RCP< const Interpolator< Scalar > > getInterpolator() const
void setInterpolator(const Teuchos::RCP< Interpolator< Scalar > > &interpolator)
Set the interpolator for this history.
ParameterList & setName(const std::string &name)
void copy(Teuchos::RCP< const SolutionHistory< Scalar > > sh)
Teuchos::RCP< SolutionState< Scalar > > findState(const Scalar time) const
Find solution state at requested time (no interpolation)
Teuchos::RCP< const Teuchos::ParameterList > getValidParameters() const
Return a valid ParameterList with current settings.
Solution state for integrators and steppers.
Teuchos::RCP< std::vector< Teuchos::RCP< SolutionState< Scalar > > > > history_