9 #ifndef Tempus_TimeEventComposite_decl_hpp
10 #define Tempus_TimeEventComposite_decl_hpp
15 #include "Tempus_config.hpp"
18 #include "Tempus_TimeEventRange.hpp"
19 #include "Tempus_TimeEventRangeIndex.hpp"
20 #include "Tempus_TimeEventList.hpp"
21 #include "Tempus_TimeEventListIndex.hpp"
32 template<
class Scalar>
41 this->
setName(
"TimeEventComposite");
47 std::string name =
"TimeEventComposite")
59 virtual std::vector<Teuchos::RCP<TimeEventBase<Scalar > > >
getTimeEvents()
const
62 std::vector<Teuchos::RCP<TimeEventBase<Scalar > > > te =
timeEvents_;
85 virtual bool isTime(Scalar time)
const
87 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
88 return isTime(time, timeEvents);
106 if (e->isTime(time)) timeEvents.push_back(e);
108 return (!timeEvents.empty());
145 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
171 typedef std::pair<Scalar, Teuchos::RCP<TimeEventBase<Scalar> > > TEPAIR;
172 std::vector<TEPAIR> timeEventPair;
174 timeEventPair.push_back(std::make_pair(e->timeOfNextEvent(time), e));
178 auto compare=[](TEPAIR a, TEPAIR b) {
return a.first < b.first; };
179 std::stable_sort(timeEventPair.begin(), timeEventPair.end(), compare);
182 Scalar tone = timeEventPair.front().first;
185 for (
auto it = timeEventPair.begin(); it != timeEventPair.end(); ++it) {
186 if ((*it).second->isTime(tone)) timeEvents.push_back((*it).second);
207 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
232 typedef std::pair<Scalar, Teuchos::RCP<TimeEventBase<Scalar> > > TEPAIR;
233 std::vector<TEPAIR> timeEventPair;
235 if (e->eventInRange(time1, time2))
236 timeEventPair.push_back(std::make_pair(e->timeOfNextEvent(time1), e));
239 auto compare = [](TEPAIR a, TEPAIR b) {
return a.first < b.first; };
240 std::stable_sort(timeEventPair.begin(), timeEventPair.end(), compare);
243 for(
auto& e : timeEventPair) timeEvents.push_back(e.second);
245 return (!timeEvents.empty());
258 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
259 return isIndex(index, timeEvents);
277 if (e->isIndex(index)) timeEvents.push_back(e);
279 return (!timeEvents.empty());
315 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
335 typedef std::pair<int, Teuchos::RCP<TimeEventBase<Scalar> > > TEPAIR;
336 std::vector<TEPAIR> timeEventPair;
338 timeEventPair.push_back(std::make_pair(e->indexOfNextEvent(index), e));
342 auto compare = [](TEPAIR a, TEPAIR b) {
return a.first < b.first; };
343 std::stable_sort(timeEventPair.begin(), timeEventPair.end(), compare);
346 int ione = timeEventPair.front().first;
349 for (
auto it = timeEventPair.begin(); it != timeEventPair.end(); ++it) {
350 if ((*it).second->isIndex(ione)) timeEvents.push_back((*it).second);
369 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
392 typedef std::pair<int, Teuchos::RCP<TimeEventBase<Scalar> > > TEPAIR;
393 std::vector<TEPAIR> timeEventPair;
395 if (e->eventInRangeIndex(index1, index2))
396 timeEventPair.push_back(std::make_pair(e->indexOfNextEvent(index1), e));
399 auto compare = [](TEPAIR a, TEPAIR b) {
return a.first < b.first; };
400 std::stable_sort(timeEventPair.begin(), timeEventPair.end(), compare);
403 for(
auto& e : timeEventPair) timeEvents.push_back(e.second);
405 return (!timeEvents.empty());
414 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
430 Scalar largestAbsTol =
timeEvents_.front()->getAbsTol();
433 if (e->getAbsTol() > largestAbsTol) largestAbsTol = e->getAbsTol();
435 for(
auto& e : timeEvents_)
436 if (e->getAbsTol()-largestAbsTol < largestAbsTol * 1.0e-14)
437 timeEvents.push_back(e);
439 return largestAbsTol;
450 std::vector<Teuchos::RCP<TimeEventBase<Scalar> > > timeEvents;
468 if (e->getLandOnExactly()) timeEvents.push_back(e);
470 return (!timeEvents.empty());
486 std::string name = timeEvent->getName();
507 void remove(std::string name)
509 for (std::size_t i = 0; i <
timeEvents_.size(); ++i) {
527 for (std::size_t i = 0; i <
timeEvents_.size(); ++i)
530 return Teuchos::null;
542 std::stringstream tecList;
543 for(std::size_t i = 0; i <
timeEvents_.size(); ++i) {
547 return tecList.str();
554 auto l_out = Teuchos::fancyOStream( out.
getOStream() );
556 l_out->setOutputToRootOnly(0);
558 *l_out <<
"TimeEventComposite:" <<
"\n"
559 <<
" name = " << this->
getName() <<
"\n"
560 <<
" Type = " << this->
getType() <<
"\n"
561 <<
" Number of TimeEvents = " << this->
getSize() <<
"\n"
563 *l_out <<
"--------------------------------------------" << std::endl;
565 (*e).describe(*l_out, verbLevel);
566 *l_out <<
"--------------------------------------------" << std::endl;
584 Teuchos::parameterList(
"Time Event Composite");
592 pl->
set(s->getName(), *s->getValidParameters());
622 template<
class Scalar>
630 if (pList == Teuchos::null || pList->
numParams() == 0)
return tec;
633 pList->
get<std::string>(
"Type",
"Composite") !=
"Composite",
635 "Error - Time Event Type != 'Composite'. (='"
636 + pList->
get<std::string>(
"Type")+
"')\n");
638 tec->setName(pList->
get(
"Name",
"From createTimeEventComposite"));
641 std::vector<std::string> teList;
643 std::string str = pList->
get<std::string>(
"Time Events");
644 std::string delimiters(
",");
645 const char* WhiteSpace =
" \t\v\r\n";
647 std::string::size_type lastPos = str.find_first_not_of(delimiters, 0);
649 std::string::size_type pos = str.find_first_of(delimiters, lastPos);
650 while ((pos != std::string::npos) || (lastPos != std::string::npos)) {
652 std::string token = str.substr(lastPos,pos-lastPos);
654 std::size_t start = token.find_first_not_of(WhiteSpace);
655 std::size_t end = token.find_last_not_of(WhiteSpace);
656 token = (start == end ? std::string() : token.substr(start, end-start+1));
658 teList.push_back(token);
659 if(pos==std::string::npos)
break;
661 lastPos = str.find_first_not_of(delimiters, pos);
662 pos = str.find_first_of(delimiters, lastPos);
666 for (
auto teName: teList) {
667 RCP<ParameterList> pl =
670 auto timeEventType = pl->get<std::string>(
"Type",
"Unknown");
671 if (timeEventType ==
"Range") {
672 tec->add(createTimeEventRange<Scalar>(pl));
673 }
else if (timeEventType ==
"Range Index") {
674 tec->add(createTimeEventRangeIndex<Scalar>(pl));
675 }
else if (timeEventType ==
"List") {
676 tec->add(createTimeEventList<Scalar>(pl));
677 }
else if (timeEventType ==
"List Index") {
678 tec->add(createTimeEventListIndex<Scalar>(pl));
680 RCP<Teuchos::FancyOStream> out =
681 Teuchos::fancyOStream(Teuchos::rcpFromRef(std::cout));
682 out->setOutputToRootOnly(0);
684 *out <<
"Warning -- createTimeEventComposite() - Unknown Time Event Type!\n"
685 <<
"'Type' = '" << timeEventType <<
"'\n"
686 <<
"Should call add() with this "
687 <<
"(app-specific?) Time Event.\n" << std::endl;
691 if (tec->getSize() == 0) {
692 RCP<Teuchos::FancyOStream> out =
693 Teuchos::fancyOStream(Teuchos::rcpFromRef(std::cout));
694 out->setOutputToRootOnly(0);
696 *out <<
"Warning -- createTimeEventComposite() - Did not\n"
697 <<
" find/recognize any TimeEvents to create!\n"
698 <<
" If there is a app-specific TimeEvent,\n"
699 <<
" explicitly add it to this TimeEventComposite.\n"
709 #endif // Tempus_TimeEventComposite_decl_hpp
virtual int indexOfNextEvent(int index, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Return the index of the next event following the input index plus the constraining TimeEvent(s)...
virtual std::string getType() const
Return the type of TimeEvent.
virtual Scalar getDefaultTime() const
Return the default time used for TimeEvents.
TimeEventComposite(std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > te, std::string name="TimeEventComposite")
Construct with full argument list of data members.
virtual bool isIndex(int index) const
Test if index is a time event.
virtual void setType(std::string s)
TimeEventComposite()
Default Constructor.
std::string getTimeEventNames() const
Return a string of the names of Time Events (comma separated).
virtual void setName(std::string name)
Set the name of the TimeEvent.
T & get(const std::string &name, T def_value)
ParameterList & set(std::string const &name, T const &value, std::string const &docString="", RCP< const ParameterEntryValidator > const &validator=null)
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
virtual bool isIndex(int index, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Test if index is a time event plus the constraining TimeEvent(s).
virtual bool getLandOnExactly(std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Return if the time events need to be landed on exactly plus the constraining TimeEvent(s).
virtual Scalar timeOfNextEvent(Scalar time, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Return the time of the next time event and constraining TimeEvent(s).
Ordinal numParams() const
virtual bool isTime(Scalar time) const
Test if time is near a TimeEvent (within tolerance).
virtual void setTimeEvents(std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > te)
Set the TimeEvents.
virtual Scalar timeToNextEvent(Scalar time, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
How much time until the next event plus the constraining TimeEvent(s).
virtual int getDefaultIndex() const
Return the default index used by TimeEvents.
virtual bool isTime(Scalar time, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Test if time is near a TimeEvent (within tolerance) plus the constraining TimeEvent(s).
void add(Teuchos::RCP< TimeEventBase< Scalar > > timeEvent)
Add TimeEvent to the TimeEvent vector.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
virtual bool eventInRange(Scalar time1, Scalar time2) const
Test if an event occurs within the time range.
virtual Scalar getAbsTol() const
Return the largest absolute tolerance from all the TimeEvents.
void clear()
Clear the TimeEvent vector.
virtual std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > getTimeEvents() const
Get a copy of the current set of TimeEvents.
virtual Scalar timeToNextEvent(Scalar time) const
How much time until the next event.
This composite TimeEvent loops over added TimeEvents.
std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > timeEvents_
std::size_t getSize() const
Return the size of the TimeEvent vector.
virtual bool eventInRangeIndex(int index1, int index2) const
Test if an event occurs within the index range.
virtual bool eventInRangeIndex(int index1, int index2, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Test if an event occurs within the index range plus the constraining TimeEvent(s).
virtual int indexToNextEvent(int index) const
How many indices until the next event.
virtual int indexOfNextEvent(int index) const
Return the index of the next event following the input index.
This class defines time events which can be used to "trigger" an action.
virtual std::string getName() const
Return the name of the TimeEvent.
Teuchos::RCP< TimeEventBase< Scalar > > find(std::string name)
Find TimeEvent based on name.
virtual void describe(Teuchos::FancyOStream &out, const Teuchos::EVerbosityLevel verbLevel) const
Describe member data.
RCP< std::basic_ostream< char_type, traits_type > > getOStream()
virtual Scalar timeOfNextEvent(Scalar time) const
Return the time of the next event following the input time.
virtual ~TimeEventComposite()
Destructor.
virtual int indexToNextEvent(int index, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
How many indices until the next event.
ParameterList & sublist(const std::string &name, bool mustAlreadyExist=false, const std::string &docString="")
ParameterList & setName(const std::string &name)
virtual bool eventInRange(Scalar time1, Scalar time2, std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Test if an event occurs within the time range plus the constraining TimeEvent(s). ...
Teuchos::RCP< TimeEventComposite< Scalar > > createTimeEventComposite(Teuchos::RCP< Teuchos::ParameterList > const &pList)
TimeEventComposite nonmember constructor via ParameterList.
virtual Teuchos::RCP< const Teuchos::ParameterList > getValidParameters() const
Return a valid ParameterList with current settings.
virtual bool getLandOnExactly() const
Return if the time events need to be landed on exactly.
virtual Scalar getAbsTol(std::vector< Teuchos::RCP< TimeEventBase< Scalar > > > &timeEvents) const
Return the largest absolute tolerance from all the TimeEvents plus the constraining TimeEvent(s)...