68int main(
int argc,
char *argv[])
75 const char *mesh_file =
"../../data/star.mesh";
82 bool use_pointwise_transfer =
false;
83 const char *device_config =
"cpu";
87 args.
AddOption(&mesh_file,
"-m",
"--mesh",
90 "Problem type (see the RHO_exact function).");
92 "Finite element order (polynomial degree) or -1 for"
93 " isoparametric space.");
94 args.
AddOption(&lref,
"-lref",
"--lor-ref-level",
"LOR refinement level.");
95 args.
AddOption(&lorder,
"-lo",
"--lor-order",
96 "LOR space order (polynomial degree, zero by default).");
97 args.
AddOption(&vis,
"-vis",
"--visualization",
"-no-vis",
99 "Enable or disable GLVis visualization.");
100 args.
AddOption(&useH1,
"-h1",
"--use-h1",
"-l2",
"--use-l2",
101 "Use H1 spaces instead of L2.");
102 args.
AddOption(&use_pointwise_transfer,
"-t",
"--use-pointwise-transfer",
103 "-no-t",
"--dont-use-pointwise-transfer",
104 "Use pointwise transfer operators instead of L2 projection.");
105 args.
AddOption(&device_config,
"-d",
"--device",
106 "Device configuration string, see Device::Configure().");
107 args.
AddOption(&use_ea,
"-ea",
"--ea-version",
"-no-ea",
108 "--no-ea-version",
"Use element assembly version.");
112 Device device(device_config);
116 Mesh serial_mesh(mesh_file, 1, 1);
117 ParMesh mesh(MPI_COMM_WORLD, serial_mesh);
122 for (
int l = 0; l < 4; l++)
141 cerr <<
"Switching the H1 LOR space order from 0 to 1\n";
190 if (use_pointwise_transfer)
206 R.
Mult(rho, rho_lor);
209 auto global_max = [](
const Vector& v)
211 real_t max = v.Normlinf();
213 MPI_MAX, MPI_COMM_WORLD);
223 P.
Mult(rho_lor, rho);
230 real_t l_inf = global_max(rho_prev_true);
234 cout <<
"|HO - P(R(HO))|_∞ = " << l_inf << endl;
240 auto global_sum = [](
const Vector& v)
244 MPI_SUM, MPI_COMM_WORLD);
254 real_t ho_dual_mass = global_sum(M_rho);
255 real_t lor_dual_mass = global_sum(M_rho_lor);
258 cout <<
"HO -> LOR dual field: " << abs(ho_dual_mass - lor_dual_mass) <<
"\n\n";
274 P.
Mult(rho_lor, rho);
281 R.
Mult(rho, rho_lor);
282 compute_mass(&fespace_lor, lor_mass, LOR_dc,
"R(P(LOR))");
283 if (vis) {
visualize(LOR_dc,
"R(P(LOR))",
Wx,
Wy, visport); }
285 rho_lor_prev -= rho_lor;
288 real_t l_inf = global_max(rho_lor_prev_true);
292 cout <<
"|LOR - R(P(LOR))|_∞ = " << l_inf << endl;
297 if (!use_pointwise_transfer)
304 real_t ho_dual_mass = global_sum(M_rho);
305 real_t lor_dual_mass = global_sum(M_rho_lor);
309 cout <<
"lor dual mass = " << lor_dual_mass <<
'\n';
310 cout <<
"ho dual mass = " << ho_dual_mass <<
'\n';
311 cout <<
"LOR -> HO dual field: " << abs(ho_dual_mass - lor_dual_mass) <<
'\n';
330 return x(1)+0.25*cos(2*M_PI*x.
Norml2());
332 return x(1)*x(1)*x(1) + 2*x(0)*x(1) + x(0);
334 return M_PI/2-atan(5*(2*x.
Norml2()-1));
336 return (x.
Norml2() < 0.1) ? 1 : 0;
353 sol_sockL2.precision(8);
355 <<
"window_geometry " << x <<
" " << y <<
" " << w <<
" " << h
356 <<
"plot_caption '" <<
space <<
" " << prefix <<
" Density'"
357 <<
"window_title '" <<
direction <<
"'" << flush;
373 cout <<
space <<
" " << prefix <<
" mass = " << newmass;
377 cout <<
" (" << fabs(newmass-massL2)*100/massL2 <<
"%)";
@ GaussLobatto
Closed type.
A coefficient that is constant across space and time.
GridFunction * GetField(const std::string &field_name)
Get a pointer to a grid function in the collection.
ParGridFunction * GetParField(const std::string &field_name)
Get a pointer to a parallel grid function in the collection.
Mesh * GetMesh()
Get a pointer to the mesh in the collection.
The MFEM Device class abstracts hardware devices such as GPUs, as well as programming models such as ...
void Print(std::ostream &out=mfem::out)
Print the configuration of the MFEM virtual device object.
Class for domain integration .
Collection of finite elements from the same family in multiple dimensions. This class is used to matc...
A general function coefficient.
void SetTrueVector()
Shortcut for calling GetTrueDofs() with GetTrueVector() as argument.
void SetFromTrueVector()
Shortcut for calling SetFromTrueDofs() with GetTrueVector() as argument.
const Vector & GetTrueVector() const
Read only access to the (optional) internal true-dof Vector.
Base class for transfer algorithms that construct transfer Operators between two finite element (FE) ...
virtual bool SupportsBackwardsOperator() const
virtual const Operator & ForwardOperator()=0
Return an Operator that transfers GridFunctions from the domain FE space to GridFunctions in the rang...
virtual const Operator & BackwardOperator()=0
Return an Operator that transfers GridFunctions from the range FE space back to GridFunctions in the ...
Arbitrary order H1-conforming (continuous) finite elements.
Wrapper for hypre's ParCSR matrix class.
HYPRE_Int Mult(HypreParVector &x, HypreParVector &y, real_t alpha=1.0, real_t beta=0.0) const
Computes y = alpha * A * x + beta * y.
static void Init()
Initialize hypre by calling HYPRE_Init() and set default options. After calling Hypre::Init(),...
Transfer data between a coarse mesh and an embedded refined mesh using interpolation.
Transfer data in L2 and H1 finite element spaces between a coarse mesh and an embedded refined mesh u...
Arbitrary order "L2-conforming" discontinuous finite elements.
void Clear()
Clear the contents of the Mesh.
int Dimension() const
Dimension of the reference space used within the elements.
void UniformRefinement(int i, const DSTable &, int *, int *, int *)
static bool Root()
Return true if the rank in MPI_COMM_WORLD is zero.
static int WorldRank()
Return the MPI rank in MPI_COMM_WORLD.
static int WorldSize()
Return the size of MPI_COMM_WORLD.
static void Init(int &argc, char **&argv, int required=default_thread_required, int *provided=nullptr)
Singleton creation with Mpi::Init(argc, argv).
virtual void Mult(const Vector &x, Vector &y) const =0
Operator application: y=A(x).
virtual void MultTranspose(const Vector &x, Vector &y) const
Action of the transpose operator: y=A^t(x). The default behavior in class Operator is to generate an ...
void ParseCheck(std::ostream &out=mfem::out)
void AddOption(bool *var, const char *enable_short_name, const char *enable_long_name, const char *disable_short_name, const char *disable_long_name, const char *description, bool required=false)
Add a boolean option and set 'var' to receive the value. Enable/disable tags are used to set the bool...
Abstract parallel finite element space.
const Operator * GetRestrictionOperator() const override
int GetTrueVSize() const override
Return the number of local vector true dofs.
Class for parallel grid function.
HypreParVector * GetTrueDofs() const
Returns the true dofs in a new HypreParVector.
void ProjectCoefficient(Coefficient &coeff) override
Project coeff Coefficient to this GridFunction. The projection computation depends on the choice of t...
Class for parallel meshes.
static ParMesh MakeRefined(ParMesh &orig_mesh, int ref_factor, int ref_type)
Create a uniformly refined (by any factor) version of orig_mesh.
real_t Norml2() const
Returns the l2 norm of the vector.
Data collection with VisIt I/O routines.
void RegisterField(const std::string &field_name, GridFunction *gf) override
Add a grid function to the collection and update the root file.
real_t compute_mass(ParFiniteElementSpace *, real_t, VisItDataCollection &, string)
void visualize(VisItDataCollection &, string, int, int, int)
real_t RHO_exact(const Vector &x)
Helper struct to convert a C++ type to an MPI type.