diff --git a/AMDiS/src/parareal/AdaptInfo.cc b/AMDiS/src/parareal/AdaptInfo.cc deleted file mode 100644 index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000 diff --git a/AMDiS/src/parareal/AdaptInfo.h b/AMDiS/src/parareal/AdaptInfo.h deleted file mode 100644 index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000 diff --git a/AMDiS/src/parareal/AdaptParaReal.cc b/AMDiS/src/parareal/AdaptParaReal.cc new file mode 100644 index 0000000000000000000000000000000000000000..8929ebaecaffaf303bd5a80f2aed6a74188128a2 --- /dev/null +++ b/AMDiS/src/parareal/AdaptParaReal.cc @@ -0,0 +1,54 @@ +#include "parareal/ProblemBase.h" +#include "parareal/AdaptParaReal.h" + +namespace AMDiS { + int AdaptParaReal::adapt() + { + int coarseStages = static_cast<int>(round(adaptInfo_->getEndTime() / coarseTimestep)); + int fineStages = static_cast<int>(round(coarseTimestep / fineTimestep)); + + adaptInfo_->setTimestep(coarseTimestep); + pararealProb->setStoreSolutions(false, true); + pararealProb->setStoreInitSolution(true); + AdaptInstationary::adapt(); + + for (int k = 0; k < pararealIter; k++) { + for (int i = 0; i < coarseStages; i++) { + adaptInfo_->resetTimeValues(fineTimestep, + i * coarseTimestep, + (i + 1) *coarseTimestep); + pararealProb->setStoreSolutions(true, false); + pararealProb->setStoreInitSolution(false); + pararealProb->setInitSolutionVec((*pararealProb->getCoarseSolutions())[i]); + pararealProb->cleanUp(); + + AdaptInstationary::adapt(); + } + + std::vector<DOFVector<double> *> coarseSolutions = + (*pararealProb->getCoarseSolutions()); + pararealProb->clearCoarseSolutions(); + + + (*pararealProb->getCoarseSolutions()).push_back(coarseSolutions[0]); + + for (int i = 1; i <= coarseStages; i++) { + adaptInfo_->resetTimeValues(coarseTimestep, + (i - 1) * coarseTimestep, + i * coarseTimestep); + pararealProb->setStoreSolutions(false, true); + pararealProb->setStoreInitSolution(false); + pararealProb->setInitSolutionVec((*pararealProb->getCoarseSolutions())[i - 1]); + + AdaptInstationary::adapt(); + + DOFVector<double>* tmp = (*pararealProb->getCoarseSolutions())[i]; + *tmp += *(*pararealProb->getFineSolutions())[(i * fineStages) - 1]; + *tmp -= *(coarseSolutions[i]); + } + } + + return 0; + } + +} diff --git a/AMDiS/src/parareal/AdaptParaReal.h b/AMDiS/src/parareal/AdaptParaReal.h new file mode 100644 index 0000000000000000000000000000000000000000..c6a66416aca885fec6a8d80716aacd3008ca85dd --- /dev/null +++ b/AMDiS/src/parareal/AdaptParaReal.h @@ -0,0 +1,87 @@ +// ============================================================================ +// == == +// == AMDiS - Adaptive multidimensional simulations == +// == == +// ============================================================================ +// == == +// == crystal growth group == +// == == +// == Stiftung caesar == +// == Ludwig-Erhard-Allee 2 == +// == 53175 Bonn == +// == germany == +// == == +// ============================================================================ +// == == +// == http://www.caesar.de/cg/AMDiS == +// == == +// ============================================================================ + +/** \file parareal/AdaptInfo.h */ + +#ifndef AMDIS_PARAREAL_ADAPTINFO_H +#define AMDIS_PARAREAL_ADAPTINFO_H + +#include "AdaptInstationary.h" +#include "parareal/ProblemBase.h" + +namespace AMDiS { + + class AdaptParaReal : public AdaptInstationary + { + public: + MEMORY_MANAGED(AdaptParaReal); + + AdaptParaReal(const char *name, + ProblemIterationInterface *problemStat, + AdaptInfo *info, + ProblemTimeInterface *problemInstat, + ParaRealProblemBase< DOFVector<double> > *paraProb, + AdaptInfo *initialInfo, + time_t initialTimestamp = 0) + : AdaptInstationary(name, problemStat, info, problemInstat, initialInfo, initialTimestamp), + coarseTimestep(0.0), + fineTimestep(0.0), + pararealIter(1), + pararealProb(paraProb) + { + GET_PARAMETER(0, static_cast<std::string>(name) + "->coarse timestep", "%f", &coarseTimestep); + GET_PARAMETER(0, static_cast<std::string>(name) + "->timestep", "%f", &fineTimestep); + GET_PARAMETER(0, static_cast<std::string>(name) + "->parareal iteration", "%d", ¶realIter); + + TEST_EXIT(fineTimestep > 0.0)("fineTimestep must be greater than zero!\n"); + TEST_EXIT(coarseTimestep > 0.0)("coarseTimestep must be greater than zero!\n"); + TEST_EXIT(fineTimestep < coarseTimestep)("fineTimestep must be smaller than coarseTimestep!\n"); + TEST_EXIT(pararealIter > 0)("ParaReal Iterations must be greater than zero!\n"); + } + + /** \brief + * Here, the parareal algorithm is executed. + */ + virtual int adapt(); + + protected: + /** \brief + * Timestep for the coarse time grid. + */ + double coarseTimestep; + + /** \brief + * Timestep for the fine time grid. + */ + double fineTimestep; + + /** \brief + * Number of parareal iterations. + */ + int pararealIter; + + /** \brief + * Pointer to the parareal problem. + */ + ParaRealProblemBase< DOFVector<double> > *pararealProb; + }; + +} + +#endif // AMDIS_PARAREAL_ADAPTINFO diff --git a/AMDiS/src/parareal/ProblemBase.cc b/AMDiS/src/parareal/ProblemBase.cc deleted file mode 100644 index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000 diff --git a/AMDiS/src/parareal/ProblemBase.h b/AMDiS/src/parareal/ProblemBase.h index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..d129a5d05014d9bcd52a934595cb1fe17e5aa5a5 100644 --- a/AMDiS/src/parareal/ProblemBase.h +++ b/AMDiS/src/parareal/ProblemBase.h @@ -0,0 +1,206 @@ +// ============================================================================ +// == == +// == AMDiS - Adaptive multidimensional simulations == +// == == +// ============================================================================ +// == == +// == crystal growth group == +// == == +// == Stiftung caesar == +// == Ludwig-Erhard-Allee 2 == +// == 53175 Bonn == +// == germany == +// == == +// ============================================================================ +// == == +// == http://www.caesar.de/cg/AMDiS == +// == == +// ============================================================================ + +/** \file parareal/ProblemBase.h */ + +#ifndef AMDIS_PARAREAL_PROBLEMBASE_H +#define AMDIS_PARAREAL_PROBLEMBASE_H + +#include <vector> +#include "CreatorInterface.h" +#include "DOFVector.h" +#include "SystemVector.h" +#include "ProblemInstat.h" + +namespace AMDiS { + + template<typename T> + class ParaRealProblemBase + { + public: + ParaRealProblemBase(CreatorInterface<T> *creator) + : storeFineSolutions(false), + storeCoarseSolutions(false), + vectorCreator(creator) + { + fineSolutions.clear(); + coarseSolutions.clear(); + } + + void storeSolution(T *vec) + { + if (storeFineSolutions) { + storeFineSolution(vec); + } + if (storeCoarseSolutions) { + storeCoarseSolution(vec); + } + } + + void storeFineSolution(T *vec) + { + T *tmp = vectorCreator->create(); + *tmp = *vec; + fineSolutions.push_back(tmp); + } + + void storeCoarseSolution(T *vec) + { + T *tmp = vectorCreator->create(); + *tmp = *vec; + coarseSolutions.push_back(tmp); + } + + void setStoreSolutions(bool fine, bool coarse) { + storeFineSolutions = fine; + storeCoarseSolutions = coarse; + } + + void setInitSolutionVec(T *vec) { + initSolutionVec = vec; + } + + void setStoreInitSolution(bool store) { + storeInitSolution = store; + } + + std::vector<T*> *getFineSolutions() { + return &fineSolutions; + } + + std::vector<T*> *getCoarseSolutions() { + return &coarseSolutions; + } + + void clearFineSolutions() { + fineSolutions.clear(); + } + + void clearCoarseSolutions() { + coarseSolutions.clear(); + } + + /** \brief + * This functions is called between switching from coarse + * time grid to fine time grid, or vice versa. Can be overwritten + * to clean up some data. + */ + virtual void cleanUp() {}; + + protected: + /** \brief + * Stores all solutions on the fine time grid. + */ + std::vector<T*> fineSolutions; + + /** \brief + * Stores all solutions on the coarse time grid. + */ + std::vector<T*> coarseSolutions; + + /** \brief + * If true, after closeTimestep() the solution is stored + * in vector \ref fineSolutions . + */ + bool storeFineSolutions; + + /** \brief + * If true, after closeTimestep() the solution is stored + * in vector \ref coarseSolution . + */ + bool storeCoarseSolutions; + + /** \brief + * If true, the initial solution is also stored in either + * \ref fineSolutions or in \ref coarseSolutions . + */ + bool storeInitSolution; + + /** \brief + * Creator interface to create new vectors (either DOFVector or + * SystemVector). + */ + CreatorInterface<T> *vectorCreator; + + /** \brief + * The initial solution for the problem can be set to this + * vector. + */ + T* initSolutionVec; + }; + + + + class ParaRealScal : public ProblemInstatScal, + public ParaRealProblemBase< DOFVector<double> > + { + public: + ParaRealScal(char* name, + ProblemScal *prob, + ProblemStatBase *initialProb = NULL) + : ProblemInstatScal(name, prob, initialProb), + ParaRealProblemBase< DOFVector<double> >(new DOFVector<double>::Creator(prob->getFESpace())) + {} + + virtual void closeTimestep(AdaptInfo *adaptInfo) { + ProblemInstatScal::closeTimestep(adaptInfo); + + storeSolution(problemStat->getSolution()); + } + + virtual void solveInitialProblem(AdaptInfo *adaptInfo) { + ProblemInstatScal::solveInitialProblem(adaptInfo); + + if (storeInitSolution) { + storeSolution(problemStat->getSolution()); + } + } + }; + + + class ParaRealVec : public ProblemInstatVec, + public ParaRealProblemBase< SystemVector > + { + public: + ParaRealVec(char *name, + ProblemVec *prob, + ProblemStatBase *initialProb = NULL) + : ProblemInstatVec(name, prob, initialProb), + ParaRealProblemBase< SystemVector >(new SystemVector::Creator(name, + prob->getFESpaces(), + prob->getNumComponents())) + {} + + virtual void closeTimestep(AdaptInfo *adaptInfo) { + ProblemInstatVec::closeTimestep(adaptInfo); + + storeSolution(problemStat->getSolution()); + } + + virtual void solveInitialProblem(AdaptInfo *adaptInfo) { + ProblemInstatVec::solveInitialProblem(adaptInfo); + + if (storeInitSolution) { + storeSolution(problemStat->getSolution()); + } + } + }; +} + +#endif