Teko  Version of the Day
 All Classes Files Functions Variables Pages
Teko_SolveInverseFactory.cpp
1 // @HEADER
2 // *****************************************************************************
3 // Teko: A package for block and physics based preconditioning
4 //
5 // Copyright 2010 NTESS and the Teko contributors.
6 // SPDX-License-Identifier: BSD-3-Clause
7 // *****************************************************************************
8 // @HEADER
9 
10 #include "Teko_SolveInverseFactory.hpp"
11 
12 // Thyra includes
13 #include "Thyra_DefaultLinearOpSource.hpp"
14 #include "Thyra_DefaultInverseLinearOp.hpp"
15 #include "Thyra_DefaultPreconditioner.hpp"
16 
17 // Stratimikos includes
18 #include "Stratimikos_DefaultLinearSolverBuilder.hpp"
19 
20 // Teko includes
21 #include "Teko_Utilities.hpp"
22 #include "Teko_BlockPreconditionerFactory.hpp"
23 #include "Teko_Preconditioner.hpp"
24 #include "Teko_PreconditionerLinearOp.hpp"
25 
26 using Teuchos::rcp;
27 using Teuchos::RCP;
28 using Teuchos::rcp_const_cast;
29 using Teuchos::rcp_dynamic_cast;
30 
31 namespace Teko {
32 
42 SolveInverseFactory::SolveInverseFactory(
43  const Teuchos::RCP<Thyra::LinearOpWithSolveFactoryBase<double> >& lowsFactory)
44  : lowsFactory_(lowsFactory) {}
45 
47 SolveInverseFactory::SolveInverseFactory(const SolveInverseFactory& siFactory)
48  : lowsFactory_(siFactory.lowsFactory_) {}
49 
59 InverseLinearOp SolveInverseFactory::buildInverse(const LinearOp& linearOp) const {
60  Teko_DEBUG_SCOPE("SolveInverseFactory::buildInverse(linearOp)", 10);
61 
62  // build and initialize inverse linear op with solve
63  Teuchos::RCP<Thyra::LinearOpWithSolveBase<double> > invLOWS = lowsFactory_->createOp();
64  lowsFactory_->initializeOp(Thyra::defaultLinearOpSource(linearOp), &*invLOWS,
65  Thyra::SUPPORT_SOLVE_FORWARD_ONLY);
66 
67  return Thyra::nonconstInverse<double>(invLOWS);
68 }
69 
82 InverseLinearOp SolveInverseFactory::buildInverse(const LinearOp& linearOp,
83  const LinearOp& precOp) const {
84  Teko_DEBUG_SCOPE("SolveInverseFactory::buildInverse(linearOp,precOp)", 10);
85 
86  // build and initialize inverse linear op with solve
87  Teuchos::RCP<Thyra::LinearOpWithSolveBase<double> > invLOWS = lowsFactory_->createOp();
88  lowsFactory_->initializePreconditionedOp(Thyra::defaultLinearOpSource(linearOp),
89  Thyra::unspecifiedPrec(precOp), &*invLOWS,
90  Thyra::SUPPORT_SOLVE_FORWARD_ONLY);
91 
92  return Thyra::nonconstInverse<double>(invLOWS);
93 }
94 
106 void SolveInverseFactory::rebuildInverse(const LinearOp& source, InverseLinearOp& dest) const {
107  RCP<Thyra::DefaultInverseLinearOp<double> > invDest =
108  rcp_dynamic_cast<Thyra::DefaultInverseLinearOp<double> >(dest);
109  RCP<Thyra::LinearOpWithSolveBase<double> > lows = invDest->getNonconstLows();
110 
111  // This stems from confusion of if the linear op with solve initializeAndResuseOp actually
112  // rebuilds the preconditioner. It seems not to and thus we have a fairly substantial problem.
113  // lowsFactory_->initializeAndReuseOp(Thyra::defaultLinearOpSource(source),&*lows);
114  lowsFactory_->initializeOp(Thyra::defaultLinearOpSource(source), &*lows);
115 }
116 
129 void SolveInverseFactory::rebuildInverse(const LinearOp& source, const LinearOp& precOp,
130  InverseLinearOp& dest) const {
131  RCP<Thyra::DefaultInverseLinearOp<double> > invDest =
132  rcp_dynamic_cast<Thyra::DefaultInverseLinearOp<double> >(dest);
133  RCP<Thyra::LinearOpWithSolveBase<double> > lows = invDest->getNonconstLows();
134 
135  // lowsFactory_->initializeAndReuseOp(Thyra::defaultLinearOpSource(source),&*lows);
136  lowsFactory_->initializePreconditionedOp(Thyra::defaultLinearOpSource(source),
137  Thyra::unspecifiedPrec(precOp), &*lows,
138  Thyra::SUPPORT_SOLVE_FORWARD_ONLY);
139 }
140 
149 Teuchos::RCP<const Teuchos::ParameterList> SolveInverseFactory::getParameterList() const {
150  return lowsFactory_->getParameterList();
151 }
152 
153 } // end namespace Teko