MFEM  v3.3
Finite element discretization library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
handle.cpp
Go to the documentation of this file.
1 // Copyright (c) 2010, Lawrence Livermore National Security, LLC. Produced at
2 // the Lawrence Livermore National Laboratory. LLNL-CODE-443211. All Rights
3 // reserved. See file COPYRIGHT for details.
4 //
5 // This file is part of the MFEM library. For more information and source code
6 // availability see http://mfem.org.
7 //
8 // MFEM is free software; you can redistribute it and/or modify it under the
9 // terms of the GNU Lesser General Public License (as published by the Free
10 // Software Foundation) version 2.1 dated February 1999.
11 
12 #include "handle.hpp"
13 #include "sparsemat.hpp"
14 
15 namespace mfem
16 {
17 
19  "Operator::Type is not supported: type_id = ";
20 
22 {
23  switch (tid)
24  {
25  case Operator::MFEM_SPARSEMAT: break;
27 #ifdef MFEM_USE_MPI
28  break;
29 #else
30  MFEM_ABORT("cannot use HYPRE parallel matrix format: "
31  "MFEM is not built with HYPRE support");
32 #endif
35 #ifdef MFEM_USE_PETSC
36  break;
37 #else
38  MFEM_ABORT("cannot use PETSc matrix formats: "
39  "MFEM is not built with PETSc support");
40 #endif
41  default:
42  MFEM_ABORT("invalid Operator::Type, type_id = " << (int)type_id);
43  }
44  return tid;
45 }
46 
47 #ifdef MFEM_USE_MPI
48 void OperatorHandle::MakeSquareBlockDiag(MPI_Comm comm, HYPRE_Int glob_size,
49  HYPRE_Int *row_starts,
50  SparseMatrix *diag)
51 {
52  if (own_oper) { delete oper; }
53 
54  switch (type_id)
55  {
57  oper = new HypreParMatrix(comm, glob_size, row_starts, diag);
58  break;
59 #ifdef MFEM_USE_PETSC
62  // Assuming that PetscInt is the same size as HYPRE_Int.
63  oper = new PetscParMatrix(comm, glob_size, row_starts, diag, type_id);
64  break;
65 #endif
66  default: MFEM_ABORT(not_supported_msg << type_id);
67  }
68  own_oper = true;
69 }
70 
72 MakeRectangularBlockDiag(MPI_Comm comm, HYPRE_Int glob_num_rows,
73  HYPRE_Int glob_num_cols, HYPRE_Int *row_starts,
74  HYPRE_Int *col_starts, SparseMatrix *diag)
75 {
76  if (own_oper) { delete oper; }
77 
78  switch (type_id)
79  {
81  oper = new HypreParMatrix(comm, glob_num_rows, glob_num_cols,
82  row_starts, col_starts, diag);
83  break;
84 #ifdef MFEM_USE_PETSC
87  // Assuming that PetscInt is the same size as HYPRE_Int.
88  oper = new PetscParMatrix(comm, glob_num_rows, glob_num_cols,
89  row_starts, col_starts, diag, type_id);
90  break;
91 #endif
92  default: MFEM_ABORT(not_supported_msg << type_id);
93  }
94  own_oper = true;
95 }
96 #endif // MFEM_USE_MPI
97 
99 {
100  MFEM_VERIFY(A.Type() == P.Type(), "type mismatch in A and P");
101  Clear();
102  switch (A.Type())
103  {
105  {
107  SparseMatrix *RA = mfem::Mult(*R, *A.As<SparseMatrix>());
108  delete R;
109  pSet(mfem::Mult(*RA, *P.As<SparseMatrix>()));
110  delete RA;
111  break;
112  }
113 #ifdef MFEM_USE_MPI
116  break;
117 #ifdef MFEM_USE_PETSC
120  {
122  break;
123  }
124 #endif
125 #endif
126  default: MFEM_ABORT(not_supported_msg << type_id);
127  }
128 }
129 
131  OperatorHandle &P)
132 {
133  MFEM_VERIFY(A.Type() == Rt.Type(), "type mismatch in A and Rt");
134  MFEM_VERIFY(A.Type() == P.Type(), "type mismatch in A and P");
135  Clear();
136  switch (A.Type())
137  {
139  {
141  *P.As<SparseMatrix>()));
142  break;
143  }
144 #ifdef MFEM_USE_MPI
147  P.As<HypreParMatrix>()));
148  break;
149 #ifdef MFEM_USE_PETSC
152  {
154  P.As<PetscParMatrix>()));
155  break;
156  }
157 #endif
158 #endif
159  default: MFEM_ABORT(not_supported_msg << type_id);
160  }
161 }
162 
164 {
165  if (own_oper) { delete oper; }
166  if (Type() == A.Type())
167  {
168  oper = A.Ptr();
169  own_oper = false;
170  return;
171  }
172  oper = NULL;
173  switch (Type()) // target type id
174  {
177  switch (A.Type()) // source type id
178  {
180 #ifdef MFEM_USE_PETSC
181  oper = new PetscParMatrix(A.As<HypreParMatrix>(), Type());
182 #endif
183  break;
184  default: break;
185  }
186  break;
187  default: break;
188  }
189  MFEM_VERIFY(oper != NULL, "conversion from type id = " << A.Type()
190  << " to type id = " << Type() << " is not supported");
191  own_oper = true;
192 }
193 
195  const Array<int> &ess_dof_list)
196 {
197  Clear();
198  switch (A.Type())
199  {
201  {
202  const int preserve_diag = 1;
203  SparseMatrix *sA = A.As<SparseMatrix>();
204  SparseMatrix *Ae = new SparseMatrix(sA->Height());
205  for (int i = 0; i < ess_dof_list.Size(); i++)
206  {
207  sA->EliminateRowCol(ess_dof_list[i], *Ae, preserve_diag);
208  }
209  Ae->Finalize();
210  pSet(Ae);
211  break;
212  }
214  {
215 #ifdef MFEM_USE_MPI
216  pSet(A.As<HypreParMatrix>()->EliminateRowsCols(ess_dof_list));
217 #else
218  MFEM_ABORT("type id = Operator::HYPRE_PARCSR requires MFEM_USE_MPI");
219 #endif
220  break;
221  }
224  {
225 #ifdef MFEM_USE_PETSC
226  pSet(A.As<PetscParMatrix>()->EliminateRowsCols(ess_dof_list));
227 #else
228  MFEM_ABORT("type id = Operator::PETSC_* requires MFEM_USE_PETSC");
229 #endif
230  break;
231  }
232  default: MFEM_ABORT(not_supported_msg << A.Type());
233  }
234 }
235 
237  const Array<int> &ess_dof_list,
238  const Vector &X, Vector &B) const
239 {
240  switch (Type())
241  {
243  {
244  A_e.As<SparseMatrix>()->AddMult(X, B, -1.);
245  As<SparseMatrix>()->PartMult(ess_dof_list, X, B);
246  break;
247  }
249  {
250 #ifdef MFEM_USE_MPI
251  mfem::EliminateBC(*As<HypreParMatrix>(), *A_e.As<HypreParMatrix>(),
252  ess_dof_list, X, B);
253 #else
254  MFEM_ABORT("type id = Operator::HYPRE_PARCSR requires MFEM_USE_MPI");
255 #endif
256  break;
257  }
260  {
261 #ifdef MFEM_USE_PETSC
262  mfem::EliminateBC(*As<PetscParMatrix>(), *A_e.As<PetscParMatrix>(),
263  ess_dof_list, X, B);
264 #else
265  MFEM_ABORT("type id = Operator::PETSC_* requires MFEM_USE_PETSC");
266 #endif
267  break;
268  }
269  default: MFEM_ABORT(not_supported_msg << Type());
270  }
271 }
272 
273 } // namespace mfem
int Size() const
Logical size of the array.
Definition: array.hpp:109
void EliminateRowsCols(const Array< int > &rows_cols, const HypreParVector &X, HypreParVector &B)
Definition: hypre.cpp:1263
void ConvertFrom(OperatorHandle &A)
Convert the given OperatorHandle A to the currently set type id.
Definition: handle.cpp:163
OpType * As() const
Return the Operator pointer statically cast to a specified OpType. Similar to the method Get()...
Definition: handle.hpp:91
Wrapper for PETSc&#39;s matrix class.
Definition: petsc.hpp:128
void Mult(const Table &A, const Table &B, Table &C)
C = A * B (as boolean matrices)
Definition: table.cpp:468
Pointer to an Operator of a specified type.
Definition: handle.hpp:34
Operator::Type Type() const
Get the currently set operator type id.
Definition: handle.hpp:86
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:236
void EliminateRowCol(int rc, const double sol, Vector &rhs, int d=0)
Definition: sparsemat.cpp:1162
Operator * oper
Definition: handle.hpp:39
static const char not_supported_msg[]
Definition: handle.hpp:37
void EliminateBC(HypreParMatrix &A, HypreParMatrix &Ae, const Array< int > &ess_dof_list, const Vector &X, Vector &B)
Definition: hypre.cpp:1435
void AddMult(const DenseMatrix &b, const DenseMatrix &c, DenseMatrix &a)
Matrix matrix multiplication. A += B * C.
Definition: densemat.cpp:2870
Data type sparse matrix.
Definition: sparsemat.hpp:38
int Height() const
Get the height (size of output) of the Operator. Synonym with NumRows().
Definition: operator.hpp:36
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:194
HypreParMatrix * RAP(HypreParMatrix *A, HypreParMatrix *P)
Returns the matrix P^t * A * P.
Definition: hypre.cpp:1385
Operator::Type CheckType(Operator::Type tid)
Definition: handle.cpp:21
void Transpose(const Table &A, Table &At, int _ncols_A)
Transpose a Table.
Definition: table.cpp:408
Operator * Ptr() const
Access the underlying Operator pointer.
Definition: handle.hpp:83
Type
Enumeration defining IDs for some classes derived from Operator.
Definition: operator.hpp:123
void Clear()
Clear the OperatorHandle, deleting the held Operator (if owned), while leaving the type id unchanged...
Definition: handle.hpp:111
void MakeSquareBlockDiag(MPI_Comm comm, HYPRE_Int glob_size, HYPRE_Int *row_starts, SparseMatrix *diag)
Reset the OperatorHandle to hold a parallel square block-diagonal matrix using the currently set type...
Definition: handle.cpp:48
void pSet(OpType *A, bool own_A=true)
Definition: handle.hpp:46
Operator::Type type_id
Definition: handle.hpp:40
void EliminateRowsCols(const Array< int > &rows_cols, const HypreParVector &X, HypreParVector &B)
Eliminate rows and columns from the matrix, and rows from the vector B. Modify B with the BC values i...
Definition: petsc.cpp:1129
void MakeRectangularBlockDiag(MPI_Comm comm, HYPRE_Int glob_num_rows, HYPRE_Int glob_num_cols, HYPRE_Int *row_starts, HYPRE_Int *col_starts, SparseMatrix *diag)
Reset the OperatorHandle to hold a parallel rectangular block-diagonal matrix using the currently set...
Definition: handle.cpp:72
Vector data type.
Definition: vector.hpp:36
Wrapper for hypre&#39;s ParCSR matrix class.
Definition: hypre.hpp:174
void MakePtAP(OperatorHandle &A, OperatorHandle &P)
Reset the OperatorHandle to hold the product P^t A P.
Definition: handle.cpp:98
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:130