Logo  0.95.0-final
Finite Element Embedded Library and Language in C++
Feel++ Feel++ on Github Feel++ community
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
preconditioner.hpp
Go to the documentation of this file.
1 /* -*- mode: c++; coding: utf-8; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; show-trailing-whitespace: t -*-
2 
3  This file is part of the Feel library
4 
5  Author(s): Christophe Prud'homme <christophe.prudhomme@feelpp.org>
6  Date: 2012-01-16
7 
8  Copyright (C) 2012 Université Joseph Fourier (Grenoble I)
9 
10  This library is free software; you can redistribute it and/or
11  modify it under the terms of the GNU Lesser General Public
12  License as published by the Free Software Foundation; either
13  version 2.1 of the License, or (at your option) any later version.
14 
15  This library is distributed in the hope that it will be useful,
16  but WITHOUT ANY WARRANTY; without even the implied warranty of
17  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18  Lesser General Public License for more details.
19 
20  You should have received a copy of the GNU Lesser General Public
21  License along with this library; if not, write to the Free Software
22  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
23 */
29 #ifndef __Preconditioner_H
30 #define __Preconditioner_H 1
31 
32 #include <boost/parameter.hpp>
34 #include <feel/feelcore/parameter.hpp>
36 #include <feel/feelalg/vector.hpp>
37 
38 #include <feel/feelalg/enums.hpp>
39 
40 namespace Feel
41 {
42 template<typename T> class Backend;
43 typedef Backend<double> backend_type;
44 typedef boost::shared_ptr<Backend<double> > backend_ptrtype;
45 
53 template<typename T>
55 {
56 public:
57 
58 
62 
63 
65 
69 
71  typedef boost::shared_ptr<Preconditioner<T> > preconditioner_ptrtype;
72 
73  typedef boost::shared_ptr<MatrixSparse<T> > sparse_matrix_ptrtype;
74  typedef boost::shared_ptr<Vector<T> > vector_ptrtype;
75 
76 
78 
82 
84  Preconditioner( std::string const& name = "", WorldComm const& worldComm=Environment::worldComm() );
85 
88  :
89  M_name(),
91  M_matrix( o.M_matrix ),
96  M_mat_has_changed( o.M_mat_has_changed )
97  {}
98 
100  ~Preconditioner();
101 
102  static preconditioner_ptrtype build( std::string const& name = "", BackendType = BACKEND_PETSC, WorldComm const& worldComm=Environment::worldComm() );
103 
107  virtual void init () {};
108 
110 
114 
117  {
118  if ( this != &o )
119  {
120  M_name = o.M_name;
122  M_matrix = o.M_matrix;
127  M_mat_has_changed = o.M_mat_has_changed;
128  }
129 
130  return *this;
131  }
132 
133  void operator()()
134  {
135  this->clear();
136  }
138 
142 
147  bool initialized () const
148  {
149  return M_is_initialized;
150  }
151 
152  WorldComm const& worldComm() const { return M_worldComm; }
153 
158  virtual void apply( const Vector<T> & x, Vector<T> & y ) = 0;
159 
164  void apply( vector_ptrtype const& x, vector_ptrtype& y )
165  {
166  this->apply( *x, *y );
167  }
168 
172  virtual void clear () {}
173 
174 
175 
180  {
181  return M_preconditioner_type;
182  }
183 
184  virtual std::string name() const { return M_name; }
185 
186  sparse_matrix_ptrtype const& matrix() const { return M_matrix; }
187 
189 
193 
194  virtual void setName( std::string const& n ) { M_name = n; }
195 
199  void setMatrix( sparse_matrix_ptrtype mat );
200 
204  void setType ( const PreconditionerType pct );
205 
209  void setMatSolverPackageType( const MatSolverPackageType mspt );
210 
214  void setPrecMatrixStructure( MatrixStructure mstruct );
215 
216 
218 
222 
223 
225 
226 
227 protected:
228 
232  std::string M_name;
233 
237  WorldComm M_worldComm;
238 
243  sparse_matrix_ptrtype M_matrix;
244 
249 
253  MatSolverPackageType M_matSolverPackage_type;
254 
259 
263  bool M_is_initialized, M_mat_has_changed;
264 
265 };
266 
268 typedef boost::shared_ptr<Preconditioner<double> > preconditioner_ptrtype;
269 
270 
271 template <typename T>
272 FEELPP_STRONG_INLINE
273 Preconditioner<T>::Preconditioner ( std::string const& name, WorldComm const& worldComm )
274 :
275 M_name(name),
276 M_worldComm(worldComm),
277 M_matrix(),
278 M_preconditioner_type ( ILU_PRECOND ),
279 M_matSolverPackage_type ( MATSOLVER_PETSC ),
280 M_prec_matrix_structure ( MatrixStructure::SAME_NONZERO_PATTERN ),
281 M_is_initialized ( false ),
282 M_mat_has_changed ( false )
283 {
284 }
285 
286 
287 
288 template <typename T>
289 FEELPP_STRONG_INLINE
291 {
292  this->clear ();
293 }
294 
296 typedef boost::shared_ptr<preconditioner_type> preconditioner_ptrtype;
297 
298 namespace detail
299 {
300 class PreconditionerManagerImpl:
301  public std::map<std::pair<backend_ptrtype,std::string>, preconditioner_ptrtype >,
302  public boost::noncopyable
303 {
304 public:
305  typedef preconditioner_ptrtype value_type;
306  typedef std::pair<backend_ptrtype,std::string> key_type;
307  typedef std::map<key_type, value_type> preconditioner_manager_type;
308 
309 };
310 typedef Feel::Singleton<PreconditionerManagerImpl> PreconditionerManager;
311 
312 struct PreconditionerManagerDeleterImpl
313 {
314  void operator()() const
315  {
316  VLOG(2) << "[PreconditionerManagerDeleter] clear PreconditionerManager Singleton: " << detail::PreconditionerManager::instance().size() << "\n";
318  VLOG(2) << "[PreconditionerManagerDeleter] clear PreconditionerManager done\n";
319  }
320 };
321 typedef Feel::Singleton<PreconditionerManagerDeleterImpl> PreconditionerManagerDeleter;
322 } // detail
323 
324 
325 BOOST_PARAMETER_MEMBER_FUNCTION( ( boost::shared_ptr<Preconditioner<double> > ),
326  preconditioner,
327  tag,
328  ( required
329  ( pc,( PreconditionerType ) )
330  ( backend, (backend_ptrtype) ) )
331  ( optional
332  ( prefix, *( boost::is_convertible<mpl::_,std::string> ), "" )
333  ( matrix,( d_sparse_matrix_ptrtype ),d_sparse_matrix_ptrtype() )
334 
335  ( pcfactormatsolverpackage,( MatSolverPackageType ), MATSOLVER_DEFAULT )
336  ( worldcomm, *, Environment::worldComm() )
337  ( rebuild, (bool), false )
338  )
339  )
340 {
341  // register the PreconditionerManager into Feel::Environment so that it gets the
342  // PreconditionerManager is cleared up when the Environment is deleted
343  static bool observed=false;
344  if ( !observed )
345  {
346  Environment::addDeleteObserver( detail::PreconditionerManagerDeleter::instance() );
347  observed = true;
348  }
349 
350 
351  Feel::detail::ignore_unused_variable_warning( args );
352 
353  auto git = detail::PreconditionerManager::instance().find( std::make_pair( backend, prefix ) );
354 
355  if ( git != detail::PreconditionerManager::instance().end() && ( rebuild == false ) )
356  {
357  VLOG(2) << "[preconditioner] found preconditioner name=" << prefix << " rebuild=" << rebuild << "\n";
358  return git->second;
359  }
360 
361  else
362  {
363 
364  preconditioner_ptrtype p = Preconditioner<double>::build( prefix, backend->type(), worldcomm );
365  p->setType( pc );
366  p->setMatSolverPackageType( pcfactormatsolverpackage );
367 
368  if ( matrix )
369  {
370  p->setMatrix( matrix );
371  }
372  VLOG(2) << "storing preconditionerin singleton" << "\n";
373  detail::PreconditionerManager::instance().operator[]( std::make_pair( backend, prefix ) ) = p;
374  backend->addDeleteObserver( p );
375  return p;
376  }
377 }
378 
379 
380 } // Feel
381 #endif /* __Preconditioner_H */

Generated on Fri Oct 25 2013 14:24:22 for Feel++ by doxygen 1.8.4