Preconditioner2InverseOperator.hpp
Go to the documentation of this file.
1/*
2 Copyright Equinor ASA 2026
3
4 This file is part of the Open Porous Media project (OPM).
5
6 OPM is free software: you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation, either version 3 of the License, or
9 (at your option) any later version.
10
11 OPM is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with OPM. If not, see <http://www.gnu.org/licenses/>.
18*/
19#ifndef OPM_PRECONDITIONER2INVERSEOPERATOR_HEADER_INCLUDED
20#define OPM_PRECONDITIONER2INVERSEOPERATOR_HEADER_INCLUDED
21
22#include <dune/common/shared_ptr.hh>
23#include <dune/istl/preconditioner.hh>
24#include <dune/istl/solver.hh>
25
26#include <memory>
27
28namespace Dune
29{
30
38template<class X>
39class Preconditioner2InverseOperator : public InverseOperator<X, X>
40{
41public:
42 using typename InverseOperator<X, X>::domain_type;
43 using typename InverseOperator<X, X>::range_type;
44 using typename InverseOperator<X, X>::field_type;
45 using typename InverseOperator<X, X>::real_type;
46 using typename InverseOperator<X, X>::scalar_real_type;
47
48 using PreconditionerType = Preconditioner<X, X>;
49
51 : prec_(stackobject_to_shared_ptr(prec))
52 {
53 }
54
55 explicit Preconditioner2InverseOperator(std::shared_ptr<PreconditionerType> prec)
56 : prec_(std::move(prec))
57 {
58 }
59
60 void apply(X& x, X& b, InverseOperatorResult& res) override
61 {
62 prec_->pre(x, b);
63 // Preconditioners compute a correction/update, so start from zero to
64 // interpret this adapter as x = M^{-1} b.
65 x = 0;
66 prec_->apply(x, b);
67 prec_->post(x);
68
69 // No residual norm is evaluated here; report one successful
70 // application rather than an iterative solve.
71 res.clear();
72 res.iterations = 1;
73 res.reduction = 1.0;
74 res.converged = true;
75 }
76
77 void apply(X& x, X& b, [[maybe_unused]] double reduction, InverseOperatorResult& res) override
78 {
79 apply(x, b, res);
80 }
81
82 SolverCategory::Category category() const override
83 {
84 return SolverCategory::category(*prec_);
85 }
86
87private:
88 // Non-owning alias when constructed from a reference, shared ownership
89 // when constructed from a shared_ptr.
90 std::shared_ptr<PreconditionerType> prec_;
91};
92
93} // namespace Dune
94
95#endif // OPM_PRECONDITIONER2INVERSEOPERATOR_HEADER_INCLUDED
Adapter exposing a preconditioner through the inverse-operator interface.
Definition: Preconditioner2InverseOperator.hpp:40
Preconditioner< X, X > PreconditionerType
Definition: Preconditioner2InverseOperator.hpp:48
Preconditioner2InverseOperator(std::shared_ptr< PreconditionerType > prec)
Definition: Preconditioner2InverseOperator.hpp:55
void apply(X &x, X &b, InverseOperatorResult &res) override
Definition: Preconditioner2InverseOperator.hpp:60
void apply(X &x, X &b, double reduction, InverseOperatorResult &res) override
Definition: Preconditioner2InverseOperator.hpp:77
Preconditioner2InverseOperator(PreconditionerType &prec)
Definition: Preconditioner2InverseOperator.hpp:50
SolverCategory::Category category() const override
Definition: Preconditioner2InverseOperator.hpp:82
Definition: fvbaseprimaryvariables.hh:161
Dune::InverseOperatorResult InverseOperatorResult
Definition: GpuBridge.hpp:32