MFEM  v4.3.0
Finite element discretization library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
handle.hpp
Go to the documentation of this file.
1 // Copyright (c) 2010-2021, Lawrence Livermore National Security, LLC. Produced
2 // at the Lawrence Livermore National Laboratory. All Rights reserved. See files
3 // LICENSE and NOTICE for details. LLNL-CODE-806117.
4 //
5 // This file is part of the MFEM library. For more information and source code
6 // availability visit https://mfem.org.
7 //
8 // MFEM is free software; you can redistribute it and/or modify it under the
9 // terms of the BSD-3 license. We welcome feedback and contributions, see file
10 // CONTRIBUTING.md for details.
11 
12 #ifndef MFEM_HANDLE_HPP
13 #define MFEM_HANDLE_HPP
14 
15 #include "../config/config.hpp"
16 #include "operator.hpp"
17 #ifdef MFEM_USE_MPI
18 #include "hypre.hpp"
19 #endif
20 
21 namespace mfem
22 {
23 
24 /// Pointer to an Operator of a specified type
25 /** This class provides a common interface for global, matrix-type operators to
26  be used in bilinear forms, gradients of nonlinear forms, static condensation,
27  hybridization, etc. The following backends are currently supported:
28  - HYPRE parallel sparse matrix (Hypre_ParCSR)
29  - PETSC globally assembled parallel sparse matrix (PETSC_MATAIJ)
30  - PETSC parallel matrix assembled on each processor (PETSC_MATIS)
31  See also Operator::Type.
32 */
34 {
35 protected:
36  static const char not_supported_msg[];
37 
40  bool own_oper;
41 
43 
44  template <typename OpType>
45  void pSet(OpType *A, bool own_A = true)
46  {
47  oper = A;
48  type_id = A->GetType();
49  own_oper = own_A;
50  }
51 
52 public:
53  /** @brief Create an OperatorHandle with type id = Operator::MFEM_SPARSEMAT
54  without allocating the actual matrix. */
56  : oper(NULL), type_id(Operator::MFEM_SPARSEMAT), own_oper(false) { }
57 
58  /** @brief Create a OperatorHandle with a specified type id, @a tid, without
59  allocating the actual matrix. */
61  : oper(NULL), type_id(CheckType(tid)), own_oper(false) { }
62 
63  /// Create an OperatorHandle for the given OpType pointer, @a A.
64  /** Presently, OpType can be SparseMatrix, HypreParMatrix, or PetscParMatrix.
65 
66  The operator ownership flag is set to the value of @a own_A.
67 
68  It is expected that @a A points to a valid object. */
69  template <typename OpType>
70  explicit OperatorHandle(OpType *A, bool own_A = true) { pSet(A, own_A); }
71 
72  ~OperatorHandle() { if (own_oper) { delete oper; } }
73 
74  /// Shallow copy. The ownership flag of the target is set to false.
76  {
77  Clear(); oper = master.oper; type_id = master.type_id; own_oper = false;
78  return *this;
79  }
80 
81  /// Access the underlying Operator pointer.
82  Operator *Ptr() const { return oper; }
83 
84  /// Support the use of -> to call methods of the underlying Operator.
85  Operator *operator->() const { return oper; }
86 
87  /// Access the underlying Operator.
88  Operator &operator*() { return *oper; }
89 
90  /// Access the underlying Operator.
91  const Operator &operator*() const { return *oper; }
92 
93  /// Get the currently set operator type id.
94  Operator::Type Type() const { return type_id; }
95 
96  /** @brief Return the Operator pointer statically cast to a specified OpType.
97  Similar to the method Get(). */
98  template <typename OpType>
99  OpType *As() const { return static_cast<OpType*>(oper); }
100 
101  /// Return the Operator pointer dynamically cast to a specified OpType.
102  template <typename OpType>
103  OpType *Is() const { return dynamic_cast<OpType*>(oper); }
104 
105  /// Return the Operator pointer statically cast to a given OpType.
106  /** Similar to the method As(), however the template type OpType can be
107  derived automatically from the argument @a A. */
108  template <typename OpType>
109  void Get(OpType *&A) const { A = static_cast<OpType*>(oper); }
110 
111  /// Return true if the OperatorHandle owns the held Operator.
112  bool OwnsOperator() const { return own_oper; }
113 
114  /// Set the ownership flag for the held Operator.
115  void SetOperatorOwner(bool own = true) { own_oper = own; }
116 
117  /** @brief Clear the OperatorHandle, deleting the held Operator (if owned),
118  while leaving the type id unchanged. */
119  void Clear()
120  {
121  if (own_oper) { delete oper; }
122  oper = NULL;
123  own_oper = false;
124  }
125 
126  /// Invoke Clear() and set a new type id.
128  {
129  Clear();
130  type_id = CheckType(tid);
131  }
132 
133  /// Reset the OperatorHandle to the given OpType pointer, @a A.
134  /** Presently, OpType can be SparseMatrix, HypreParMatrix, or PetscParMatrix.
135 
136  The operator ownership flag is set to the value of @a own_A.
137 
138  It is expected that @a A points to a valid object. */
139  template <typename OpType>
140  void Reset(OpType *A, bool own_A = true)
141  {
142  if (own_oper) { delete oper; }
143  pSet(A, own_A);
144  }
145 
146 #ifdef MFEM_USE_MPI
147  /** @brief Reset the OperatorHandle to hold a parallel square block-diagonal
148  matrix using the currently set type id. */
149  /** The operator ownership flag is set to true. */
150  void MakeSquareBlockDiag(MPI_Comm comm, HYPRE_BigInt glob_size,
151  HYPRE_BigInt *row_starts, SparseMatrix *diag);
152 
153  /** @brief Reset the OperatorHandle to hold a parallel rectangular
154  block-diagonal matrix using the currently set type id. */
155  /** The operator ownership flag is set to true. */
156  void MakeRectangularBlockDiag(MPI_Comm comm, HYPRE_BigInt glob_num_rows,
157  HYPRE_BigInt glob_num_cols, HYPRE_BigInt *row_starts,
158  HYPRE_BigInt *col_starts, SparseMatrix *diag);
159 #endif // MFEM_USE_MPI
160 
161  /// Reset the OperatorHandle to hold the product @a P^t @a A @a P.
162  /** The type id of the result is determined by that of @a A and @a P. The
163  operator ownership flag is set to true. */
165 
166  /** @brief Reset the OperatorHandle to hold the product R @a A @a P, where
167  R = @a Rt^t. */
168  /** The type id of the result is determined by that of @a Rt, @a A, and @a P.
169  The operator ownership flag is set to true. */
171 
172  /// Convert the given OperatorHandle @a A to the currently set type id.
173  /** The operator ownership flag is set to false if the object held by @a A
174  will be held by this object as well, e.g. when the source and destination
175  types are the same; otherwise it is set to true. */
176  void ConvertFrom(OperatorHandle &A);
177 
178  /// Convert the given OpType pointer, @a A, to the currently set type id.
179  /** This method creates a temporary OperatorHandle for @a A and invokes
180  ConvertFrom(OperatorHandle &) with it. */
181  template <typename OpType>
182  void ConvertFrom(OpType *A)
183  {
184  OperatorHandle Ah(A, false);
185  ConvertFrom(Ah);
186  }
187 
188  /** @brief Reset the OperatorHandle to be the eliminated part of @a A after
189  elimination of the essential dofs @a ess_dof_list. */
190  void EliminateRowsCols(OperatorHandle &A, const Array<int> &ess_dof_list);
191 
192  /// Eliminate the rows corresponding to the essential dofs @a ess_dof_list
193  void EliminateRows(const Array<int> &ess_dof_list);
194 
195  /// Eliminate columns corresponding to the essential dofs @a ess_dof_list
196  void EliminateCols(const Array<int> &ess_dof_list);
197 
198  /// Eliminate essential dofs from the solution @a X into the r.h.s. @a B.
199  /** The argument @a A_e is expected to be the result of the method
200  EliminateRowsCols(). */
201  void EliminateBC(const OperatorHandle &A_e, const Array<int> &ess_dof_list,
202  const Vector &X, Vector &B) const;
203 };
204 
205 
206 /// Add an alternative name for OperatorHandle -- OperatorPtr.
208 
209 } // namespace mfem
210 
211 #endif
OperatorHandle()
Create an OperatorHandle with type id = Operator::MFEM_SPARSEMAT without allocating the actual matrix...
Definition: handle.hpp:55
void ConvertFrom(OperatorHandle &A)
Convert the given OperatorHandle A to the currently set type id.
Definition: handle.cpp:200
OpType * As() const
Return the Operator pointer statically cast to a specified OpType. Similar to the method Get()...
Definition: handle.hpp:99
const Operator & operator*() const
Access the underlying Operator.
Definition: handle.hpp:91
Pointer to an Operator of a specified type.
Definition: handle.hpp:33
Operator::Type Type() const
Get the currently set operator type id.
Definition: handle.hpp:94
void EliminateBC(const OperatorHandle &A_e, const Array< int > &ess_dof_list, const Vector &X, Vector &B) const
Eliminate essential dofs from the solution X into the r.h.s. B.
Definition: handle.cpp:340
void EliminateRows(const Array< int > &ess_dof_list)
Eliminate the rows corresponding to the essential dofs ess_dof_list.
Definition: handle.cpp:303
Operator * oper
Definition: handle.hpp:38
void EliminateCols(const Array< int > &ess_dof_list)
Eliminate columns corresponding to the essential dofs ess_dof_list.
Definition: handle.cpp:321
static const char not_supported_msg[]
Definition: handle.hpp:36
Operator & operator*()
Access the underlying Operator.
Definition: handle.hpp:88
OpType * Is() const
Return the Operator pointer dynamically cast to a specified OpType.
Definition: handle.hpp:103
Data type sparse matrix.
Definition: sparsemat.hpp:41
void EliminateRowsCols(OperatorHandle &A, const Array< int > &ess_dof_list)
Reset the OperatorHandle to be the eliminated part of A after elimination of the essential dofs ess_d...
Definition: handle.cpp:252
Operator::Type CheckType(Operator::Type tid)
Definition: handle.cpp:32
Operator * operator->() const
Support the use of -&gt; to call methods of the underlying Operator.
Definition: handle.hpp:85
Operator * Ptr() const
Access the underlying Operator pointer.
Definition: handle.hpp:82
void MakeRectangularBlockDiag(MPI_Comm comm, HYPRE_BigInt glob_num_rows, HYPRE_BigInt glob_num_cols, HYPRE_BigInt *row_starts, HYPRE_BigInt *col_starts, SparseMatrix *diag)
Reset the OperatorHandle to hold a parallel rectangular block-diagonal matrix using the currently set...
Definition: handle.cpp:91
Type
Enumeration defining IDs for some classes derived from Operator.
Definition: operator.hpp:252
void MakeSquareBlockDiag(MPI_Comm comm, HYPRE_BigInt glob_size, HYPRE_BigInt *row_starts, SparseMatrix *diag)
Reset the OperatorHandle to hold a parallel square block-diagonal matrix using the currently set type...
Definition: handle.cpp:60
bool OwnsOperator() const
Return true if the OperatorHandle owns the held Operator.
Definition: handle.hpp:112
OperatorHandle OperatorPtr
Add an alternative name for OperatorHandle – OperatorPtr.
Definition: handle.hpp:207
OperatorHandle(Operator::Type tid)
Create a OperatorHandle with a specified type id, tid, without allocating the actual matrix...
Definition: handle.hpp:60
HYPRE_Int HYPRE_BigInt
void ConvertFrom(OpType *A)
Convert the given OpType pointer, A, to the currently set type id.
Definition: handle.hpp:182
void Clear()
Clear the OperatorHandle, deleting the held Operator (if owned), while leaving the type id unchanged...
Definition: handle.hpp:119
void SetOperatorOwner(bool own=true)
Set the ownership flag for the held Operator.
Definition: handle.hpp:115
void pSet(OpType *A, bool own_A=true)
Definition: handle.hpp:45
Operator::Type type_id
Definition: handle.hpp:39
void Get(OpType *&A) const
Return the Operator pointer statically cast to a given OpType.
Definition: handle.hpp:109
Vector data type.
Definition: vector.hpp:60
OperatorHandle & operator=(const OperatorHandle &master)
Shallow copy. The ownership flag of the target is set to false.
Definition: handle.hpp:75
Abstract operator.
Definition: operator.hpp:24
void MakePtAP(OperatorHandle &A, OperatorHandle &P)
Reset the OperatorHandle to hold the product P^t A P.
Definition: handle.cpp:123
void SetType(Operator::Type tid)
Invoke Clear() and set a new type id.
Definition: handle.hpp:127
void MakeRAP(OperatorHandle &Rt, OperatorHandle &A, OperatorHandle &P)
Reset the OperatorHandle to hold the product R A P, where R = Rt^t.
Definition: handle.cpp:161
OperatorHandle(OpType *A, bool own_A=true)
Create an OperatorHandle for the given OpType pointer, A.
Definition: handle.hpp:70
void Reset(OpType *A, bool own_A=true)
Reset the OperatorHandle to the given OpType pointer, A.
Definition: handle.hpp:140