Skip to content
Snippets Groups Projects
Commit 3cafec5b authored by Markus Blatt's avatar Markus Blatt
Browse files

Makes shallow copies of twolevel method usable in different threads.

The LevelTransferPolicies have internal storage for lhs and rhs that
should be cloned in each copy to prevent overwriting values. This
patch accomplishes this.
parent fc5fd4c5
No related branches found
No related tags found
No related merge requests found
......@@ -73,14 +73,14 @@ void testTwoLevelMethod()
TransferPolicy; // Policy for coarse linear system creation
typedef Dune::Amg::OneStepAMGCoarseSolverPolicy<Operator,CSmoother, Criterion>
CoarsePolicy; // Policy for coarse solver creation
typedef typename Dune::Amg::SmootherTraits<CSmoother>::Arguments SmootherArgs;
typedef Dune::Amg::SmootherTraits<CSmoother>::Arguments SmootherArgs;
Criterion crit;
CoarsePolicy coarsePolicy=CoarsePolicy(SmootherArgs(), crit);
TransferPolicy transferPolicy(crit);
Operator fop(mat);
Dune::Amg::TwoLevelMethod<Operator,Operator,FSmoother> preconditioner(fop,
Dune::stackobject_to_shared_ptr(fineSmoother),
Dune::stackobject_to_shared_ptr<Dune::Amg::LevelTransferPolicy<Operator,Operator> >(transferPolicy),
transferPolicy,
coarsePolicy);
Dune::GeneralizedPCGSolver<Vector> amgCG(fop,preconditioner,1e-8,80,2);
Dune::InverseOperatorResult res;
......
......@@ -114,6 +114,9 @@ public:
*/
virtual void createCoarseLevelSystem(const FineOperatorType& fineOperator)=0;
/** @brief Clone the current object. */
virtual LevelTransferPolicy* clone() const =0;
protected:
/** @brief The coarse level rhs. */
CoarseRangeType rhs_;
......@@ -203,6 +206,11 @@ public:
prolongDamp_, ParallelInformation());
}
AggregationLevelTransferPolicy* clone() const
{
return new AggregationLevelTransferPolicy(*this);
}
private:
typename O::matrix_type::field_type prolongDamp_;
shared_ptr<AggregatesMap> aggregatesMap_;
......@@ -365,17 +373,30 @@ public:
template<class CoarseSolverPolicy>
TwoLevelMethod(const FineOperatorType& op,
shared_ptr<SmootherType> smoother,
shared_ptr<LevelTransferPolicy<FineOperatorType,
CoarseOperatorType> > policy,
const LevelTransferPolicy<FineOperatorType,
CoarseOperatorType>& policy,
CoarseSolverPolicy& coarsePolicy,
std::size_t preSteps=1, std::size_t postSteps=1)
: operator_(op), smoother_(smoother), policy_(policy),
: operator_(&op), smoother_(smoother),
preSteps_(preSteps), postSteps_(postSteps)
{
policy_->createCoarseLevelSystem(operator_);
policy_ = policy.clone();
policy_->createCoarseLevelSystem(*operator_);
coarseSolver_.reset(coarsePolicy.createCoarseLevelSolver(*policy_));
}
TwoLevelMethod(const TwoLevelMethod& other)
: operator_(other.operator_), coarseSolver_(other.coarseSolver_),
smoother_(other.smoother_), policy_(other.policy_.clone()),
preSteps_(preSteps_), postSteps_(postSteps_)
{}
~TwoLevelMethod()
{
// Each instance has its own policy.
delete policy_;
}
void pre(FineDomainType& x, FineRangeType& b)
{
smoother_->pre(x,b);
......@@ -395,7 +416,7 @@ public:
context.update=&v;
context.smoother=smoother_;
context.rhs=&rhs;
context.matrix=&operator_;
context.matrix=operator_;
// Presmoothing
presmooth(context, preSteps_);
//Coarse grid correction
......@@ -443,14 +464,14 @@ private:
*/
const FineOperatorType* matrix;
};
const FineOperatorType& operator_;
const FineOperatorType* operator_;
/** @brief The coarse level solver. */
shared_ptr<InverseOperator<typename CO::domain_type,
typename CO::range_type> > coarseSolver_;
/** @brief The fine level smoother. */
shared_ptr<S> smoother_;
/** @brief Policy for prolongation, restriction, and coarse level system creation. */
shared_ptr<LevelTransferPolicy<FO,CO> > policy_;
LevelTransferPolicy<FO,CO>* policy_;
/** @brief The number of presmoothing steps to apply. */
std::size_t preSteps_;
/** @brief The number of postsmoothing steps to apply. */
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment