Teko Version of the Day
Loading...
Searching...
No Matches
Teko_PreconditionerInverseFactory.cpp
1/*
2// @HEADER
3//
4// ***********************************************************************
5//
6// Teko: A package for block and physics based preconditioning
7// Copyright 2010 Sandia Corporation
8//
9// Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
10// the U.S. Government retains certain rights in this software.
11//
12// Redistribution and use in source and binary forms, with or without
13// modification, are permitted provided that the following conditions are
14// met:
15//
16// 1. Redistributions of source code must retain the above copyright
17// notice, this list of conditions and the following disclaimer.
18//
19// 2. Redistributions in binary form must reproduce the above copyright
20// notice, this list of conditions and the following disclaimer in the
21// documentation and/or other materials provided with the distribution.
22//
23// 3. Neither the name of the Corporation nor the names of the
24// contributors may be used to endorse or promote products derived from
25// this software without specific prior written permission.
26//
27// THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
28// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
30// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
31// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
32// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
33// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
34// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
35// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
36// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
37// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
38//
39// Questions? Contact Eric C. Cyr (eccyr@sandia.gov)
40//
41// ***********************************************************************
42//
43// @HEADER
44
45*/
46
47/*
48// @header
49//
50// ***********************************************************************
51//
52// teko: a package for block and physics based preconditioning
53// copyright 2010 sandia corporation
54//
55// under the terms of contract de-ac04-94al85000 with sandia corporation,
56// the u.s. government retains certain rights in this software.
57//
58// redistribution and use in source and binary forms, with or without
59// modification, are permitted provided that the following conditions are
60// met:
61//
62// 1. redistributions of source code must retain the above copyright
63// notice, this list of conditions and the following disclaimer.
64//
65// 2. redistributions in binary form must reproduce the above copyright
66// notice, this list of conditions and the following disclaimer in the
67// documentation and/or other materials provided with the distribution.
68//
69// 3. neither the name of the corporation nor the names of the
70// contributors may be used to endorse or promote products derived from
71// this software without specific prior written permission.
72//
73// this software is provided by sandia corporation "as is" and any
74// express or implied warranties, including, but not limited to, the
75// implied warranties of merchantability and fitness for a particular
76// purpose are disclaimed. in no event shall sandia corporation or the
77// contributors be liable for any direct, indirect, incidental, special,
78// exemplary, or consequential damages (including, but not limited to,
79// procurement of substitute goods or services; loss of use, data, or
80// profits; or business interruption) however caused and on any theory of
81// liability, whether in contract, strict liability, or tort (including
82// negligence or otherwise) arising in any way out of the use of this
83// software, even if advised of the possibility of such damage.
84//
85// questions? contact eric c. cyr (eccyr@sandia.gov)
86//
87// ***********************************************************************
88//
89// @header
90*/
91
92#include "Teko_PreconditionerInverseFactory.hpp"
93
94// Thyra includes
95#include "Thyra_DefaultLinearOpSource.hpp"
96#include "Thyra_DefaultInverseLinearOp.hpp"
97#include "Thyra_DefaultPreconditioner.hpp"
98
99// Stratimikos includes
100#include "Stratimikos_DefaultLinearSolverBuilder.hpp"
101
102// Teko includes
103#include "Teko_Utilities.hpp"
104#include "Teko_BlockPreconditionerFactory.hpp"
105#include "Teko_Preconditioner.hpp"
106#include "Teko_PreconditionerLinearOp.hpp"
107#include "Teko_SolveInverseFactory.hpp"
108
109using Teuchos::rcp;
110using Teuchos::rcp_const_cast;
111using Teuchos::rcp_dynamic_cast;
112using Teuchos::RCP;
113
114namespace Teko {
115
125PreconditionerInverseFactory::PreconditionerInverseFactory(
126 const Teuchos::RCP<Thyra::PreconditionerFactoryBase<double> > & precFactory,
127 const Teuchos::RCP<Teko::RequestHandler> & rh)
128 : precFactory_(precFactory)
129{
130 setRequestHandler(rh);
131}
132
147PreconditionerInverseFactory::PreconditionerInverseFactory(
148 const Teuchos::RCP<Thyra::PreconditionerFactoryBase<double> > & precFactory,
149 const Teuchos::RCP<const Teuchos::ParameterList> & xtraParam,
150 const Teuchos::RCP<Teko::RequestHandler> & rh)
151 : precFactory_(precFactory)
152{
153 if(xtraParam!=Teuchos::null)
154 extraParams_ = rcp(new Teuchos::ParameterList(*xtraParam));
155 else
156 extraParams_ = Teuchos::null; // make it explicit
157
158 setRequestHandler(rh);
159}
160
162PreconditionerInverseFactory::PreconditionerInverseFactory(const PreconditionerInverseFactory & pFactory)
163 : precFactory_(pFactory.precFactory_)
164{
165 setRequestHandler(pFactory.getRequestHandler());
166}
167
177InverseLinearOp PreconditionerInverseFactory::buildInverse(const LinearOp & linearOp) const
178{
179 RCP<Thyra::PreconditionerBase<double> > prec = precFactory_->createPrec();
180 precFactory_->initializePrec(Thyra::defaultLinearOpSource(linearOp),&*prec);
181
182 RCP<Teko::PreconditionerLinearOp<double> > precOp
183 = rcp(new Teko::PreconditionerLinearOp<double>(prec));
184
185 return precOp;
186}
187
200InverseLinearOp PreconditionerInverseFactory::buildInverse(const LinearOp & linearOp, const PreconditionerState & parentState) const
201{
202 Teko_DEBUG_SCOPE("PreconditionerInverseFactory::buildInverse(A,parentState)",10);
203 RCP<Thyra::PreconditionerBase<double> > prec = precFactory_->createPrec();
204
205 {
206 Teko_DEBUG_SCOPE("Casting to Teko::Preconditioner",10);
207 // pass state downward if a Teko::Preconditioner object is begin used
208 RCP<Teko::Preconditioner> tekoPrec = Teuchos::rcp_dynamic_cast<Teko::Preconditioner>(prec);
209 if(tekoPrec!=Teuchos::null) {
210 Teko_DEBUG_SCOPE("Merging states",10);
211 tekoPrec->mergeStateObject(parentState);
212 }
213 }
214
215 precFactory_->initializePrec(Thyra::defaultLinearOpSource(linearOp),&*prec);
216
217 RCP<Teko::PreconditionerLinearOp<double> > precOp
218 = rcp(new Teko::PreconditionerLinearOp<double>(prec));
219
220 return precOp;
221}
222
234void PreconditionerInverseFactory::rebuildInverse(const LinearOp & source,InverseLinearOp & dest) const
235{
236 Teko_DEBUG_MSG("BEGIN PreconditionerInverseFactory::rebuildInverse",10);
237
238 RCP<Thyra::PreconditionerBase<double> > prec
239 = Teuchos::rcp_dynamic_cast<Teko::PreconditionerLinearOp<double> >(dest)->getNonconstPreconditioner();
240
241 precFactory_->initializePrec(Thyra::defaultLinearOpSource(source),&*prec);
242
243 Teko_DEBUG_MSG("END PreconditionerInverseFactory::rebuildInverse",10);
244}
245
254Teuchos::RCP<const Teuchos::ParameterList> PreconditionerInverseFactory::getParameterList() const
255{
256 return precFactory_->getParameterList();
257}
258
273Teuchos::RCP<Teuchos::ParameterList> PreconditionerInverseFactory::getRequestedParameters() const
274{
275 Teuchos::RCP<BlockPreconditionerFactory> bpf = rcp_dynamic_cast<BlockPreconditionerFactory>(precFactory_);
276
277 // request the parameters from a BPF is required
278 if(bpf!=Teuchos::null)
279 return bpf->getRequestedParameters();
280
281 // for non block preconditioners see if there are user requested additional parameters
282 return extraParams_;
283}
284
298bool PreconditionerInverseFactory::updateRequestedParameters(const Teuchos::ParameterList & pl)
299{
300 Teuchos::RCP<BlockPreconditionerFactory> bpf = rcp_dynamic_cast<BlockPreconditionerFactory>(precFactory_);
301
302 // update the parameters of a BPF is required
303 if(bpf!=Teuchos::null)
304 return bpf->updateRequestedParameters(pl);
305
306 // for non block preconditioners see if there are user requested additional parameters
307 if(extraParams_==Teuchos::null)
308 return true;
309
310 Teuchos::ParameterList::ConstIterator itr;
311 RCP<Teuchos::ParameterList> srcPl = precFactory_->unsetParameterList();
312
313 // find name of settings sublist
314 std::string subName = "";
315 for(itr=srcPl->begin();itr!=srcPl->end();++itr) {
316 // search for std::string with "Settings" in name
317 if(itr->first.find("Settings")!=std::string::npos) {
318 subName = itr->first;
319 continue;
320 }
321 }
322
323 // update fails if no settings list was found
324 if(subName=="") {
325 precFactory_->setParameterList(srcPl);
326 return false;
327 }
328
329 // add extra parameters to list
330 Teuchos::ParameterList & settingsList = srcPl->sublist(subName);
331 for(itr=pl.begin();itr!=pl.end();++itr) {
332 if(extraParams_->isParameter(itr->first))
333 settingsList.setEntry(itr->first,itr->second);
334 }
335
336 // set the parameter list
337 precFactory_->setParameterList(srcPl);
338
339 return true;
340}
341
342void PreconditionerInverseFactory::setupParameterListFromRequestHandler()
343{
344 // for non block preconditioners see if there are user requested additional parameters
345 if(extraParams_==Teuchos::null)
346 return;
347
348 Teuchos::ParameterList::ConstIterator itr;
349 RCP<Teuchos::ParameterList> srcPl = precFactory_->unsetParameterList();
350
351 // find name of settings sublist
352 std::string subName = "";
353 for(itr=srcPl->begin();itr!=srcPl->end();++itr) {
354 // search for std::string with "Settings" in name
355 if(itr->first.find("Settings")!=std::string::npos) {
356 subName = itr->first;
357 continue;
358 }
359 }
360
361 // update fails if no settings list was found
362 /*
363 if(subName=="") {
364 precFactory_->setParameterList(srcPl);
365 return;
366 }*/
367
368 Teuchos::RCP<Teko::RequestHandler> rh = getRequestHandler();
369 TEUCHOS_TEST_FOR_EXCEPTION(rh==Teuchos::null,std::runtime_error,
370 "PreconditionerInverseFactory::setupParameterListFromRequestHandler: no request handler set");
371
372 // add extra parameters to list
373 rh->preRequest<Teuchos::RCP<Teuchos::ParameterList> >(RequestMesg(extraParams_));
374 Teuchos::RCP<Teuchos::ParameterList> requestParams =
375 rh->request<Teuchos::RCP<Teuchos::ParameterList> >(RequestMesg(extraParams_));
376
377 TEUCHOS_TEST_FOR_EXCEPTION(requestParams==Teuchos::null,std::runtime_error,"User specified request not satisfied!");
378
379 // If there is no Settings sublist, assume that the list itself contains the settings
380 if(subName==""){
381 for(itr=requestParams->begin();itr!=requestParams->end();++itr)
382 srcPl->setEntry(itr->first,itr->second);
383 }else{
384 Teuchos::ParameterList & settingsList = srcPl->sublist(subName);
385 for(itr=requestParams->begin();itr!=requestParams->end();++itr)
386 settingsList.setEntry(itr->first,itr->second);
387 }
388
389 // reset with updated parameter list
390 precFactory_->setParameterList(srcPl);
391}
392
393}