34 iso =
true; aniso =
true;
37 MFEM_VERIFY(iso || aniso,
"Metric type not supported in hr-adaptivity.");
40 const int num_ref_types = 3 + 4*(
dim-2);
45 Vector amr_base_energy(NEorig), amr_temp_energy(NEorig);
50 for (
int i = 1; i < num_ref_types+1; i++)
52 if (
dim == 2 && i < 3 && aniso !=
true ) {
continue; }
53 if (
dim == 2 && i == 3 && iso !=
true ) {
continue; }
54 if (
dim == 3 && i < 7 && aniso !=
true ) {
continue; }
55 if (
dim == 3 && i == 7 && iso !=
true ) {
continue; }
59 for (
int e = 0; e < NEorig; e++)
76 for (
int i = 0; i < amr_base_energy.Size(); i++)
91 const int NE = fes->
GetNE();
97 el_energy_vec = std::numeric_limits<float>::max();
99 for (
int e = 0; e < NE; e++)
116 int ref_access = reftype == 0 ? 0 : 1;
123 int ref_access = reftype == 0 ? 0 : 1;
130 MFEM_VERIFY(
QuadIntRule[reftype],
" Integration rule does not exist.");
137 int ref_access = reftype == 0 ? 0 : 1;
143 MFEM_ABORT(
"Incompatible geometry type!");
147 el_energy_vec(e) = 0.;
156 for (
int i = 0; i < integs.
Size(); i++)
170 for (
int j = 0; j < ati.
Size(); j++)
172 el_energy_vec(e) += ati[j]->GetRefinementElementEnergy(*fes->
GetFE(e),
187 Mesh base_mesh_copy(meshsplit);
192 for (
int i = 7; i < 8; i++)
195 Mesh mesh_ref(base_mesh_copy);
196 for (
int e = 0; e < mesh_ref.
GetNE(); e++)
212 Mesh base_mesh_copy(meshsplit);
217 for (
int i = 1; i < 4; i++)
220 Mesh mesh_ref(base_mesh_copy);
221 for (
int e = 0; e < mesh_ref.
GetNE(); e++)
236 const int Nvert = 3, NEsplit = 1;
237 Mesh meshsplit(2, Nvert, NEsplit, 0, 2);
238 const real_t tri_v[3][2] =
240 {0, 0}, {1, 0}, {0, 1}
242 const int tri_e[1][3] =
247 for (
int j = 0; j < Nvert; j++)
254 Mesh base_mesh_copy(meshsplit);
260 for (
int i = 1; i < 2; i++)
263 Mesh mesh_ref(base_mesh_copy);
264 for (
int e = 0; e < mesh_ref.
GetNE(); e++)
279 const int Nvert = 4, NEsplit = 1;
280 Mesh meshsplit(3, Nvert, NEsplit, 0, 3);
281 const real_t tet_v[4][3] =
283 {0, 0, 0}, {1, 0, 0}, {0, 1, 0}, {0, 0, 1}
285 const int tet_e[1][4] =
290 for (
int j = 0; j < Nvert; j++)
294 meshsplit.
AddTet(tet_e[0], 1);
297 Mesh base_mesh_copy(meshsplit);
303 for (
int i = 1; i < 2; i++)
306 Mesh mesh_ref(base_mesh_copy);
307 for (
int e = 0; e < mesh_ref.
GetNE(); e++)
324 const int NEsplit = meshsplit.
GetNE();
326 const int pts_cnt = NEsplit * dof_cnt;
337 for (
int i = 0; i < NEsplit; i++)
341 for (
int j = 0; j < dof_cnt; j++)
349 irule->
IntPoint(pt_id).
Set3(pos(j, 0), pos(j, 1), pos(j, 2));
375 real_t threshold = std::numeric_limits<float>::max();
398 Table coarse_to_fine;
402 for (
int pe = 0; pe < coarse_to_fine.
Size(); pe++)
404 coarse_to_fine.
GetRow(pe, tabrow);
405 int nchild = tabrow.
Size();
406 real_t parent_energy = coarse_energy(pe);
407 for (
int fe = 0; fe < nchild; fe++)
409 int child = tabrow[fe];
410 MFEM_VERIFY(child < mesh->GetNE(),
" invalid coarse to fine mapping");
411 fine_energy(child) -= parent_energy;
428 real_t threshold = std::numeric_limits<float>::max();
451 Table coarse_to_fine;
455 for (
int pe = 0; pe < meshcopy.
GetNE(); pe++)
457 coarse_to_fine.
GetRow(pe, tabrow);
458 int nchild = tabrow.
Size();
459 real_t parent_energy = coarse_energy(pe);
460 for (
int fe = 0; fe < nchild; fe++)
462 int child = tabrow[fe];
463 MFEM_VERIFY(child < pmesh->GetNE(),
" invalid coarse to fine mapping");
464 fine_energy(child) -= parent_energy;
486 for (
int i = 0; i < integs.
Size(); i++)
499 for (
int j = 0; j < ati.
Size(); j++)
513 const int cNE = cmesh.
GetNE();
524 for (
int j = 0; j < cNE; j++)
526 fe = fespace->
GetFE(j);
537 bool move_bnd_,
bool hradaptivity_,
538 int mesh_poly_deg_,
int amr_metric_id_,
539 int hr_iter_,
int h_per_r_iter_) :
540 mesh(&mesh_), nlf(&nlf_), tmopns(&tmopns_), x(&x_),
541 gridfuncarr(), fespacearr(),
542 move_bnd(move_bnd_), hradaptivity(hradaptivity_),
543 mesh_poly_deg(mesh_poly_deg_), amr_metric_id(amr_metric_id_),
544 serial(true), hr_iter(hr_iter_), h_per_r_iter(h_per_r_iter_)
560 bool move_bnd_,
bool hradaptivity_,
561 int mesh_poly_deg_,
int amr_metric_id_,
562 int hr_iter_,
int h_per_r_iter_) :
563 mesh(&pmesh_), nlf(&pnlf_), tmopns(&tmopns_), x(&px_),
564 gridfuncarr(), fespacearr(),
565 move_bnd(move_bnd_), hradaptivity(hradaptivity_),
566 mesh_poly_deg(mesh_poly_deg_), amr_metric_id(amr_metric_id_),
567 pmesh(&pmesh_), pnlf(&pnlf_), pgridfuncarr(), pfespacearr(),
568 serial(false), hr_iter(hr_iter_), h_per_r_iter(h_per_r_iter_)
607 if (fes_mesh_nodes->IsDGSpace())
608 { MFEM_ABORT(
"Periodic HR-adaptivity is not implemented yet."); }
610 bool radaptivity =
true;
617 for (
int i_hr = 0; i_hr <
hr_iter; i_hr++)
623 mfem::out << i_hr <<
" r-adaptivity iteration.\n";
629 mfem::out <<
"TMOP energy after r-adaptivity: "
631 <<
", Elements: " <<
mesh->
GetNE() << std::endl;
641 mfem::out <<
"TMOP energy after derefinement: "
643 <<
", Elements: " <<
mesh->
GetNE() << std::endl;
648 mfem::out <<
"TMOP energy after refinement: " <<
650 ", Elements: " <<
mesh->
GetNE() << std::endl;
655 mfem::out <<
"AMR stopping criterion satisfied. Stop.\n";
666 for (
int i_hr = 0; i_hr <
hr_iter; i_hr++)
672 if (myid == 0) {
mfem::out << i_hr <<
" r-adaptivity iteration.\n"; }
681 mfem::out <<
"TMOP energy after r-adaptivity: " << tmopenergy <<
682 ", Elements: " << NEGlob << std::endl;
700 mfem::out <<
"TMOP energy after derefinement: " << tmopenergy <<
701 ", Elements: " << NEGlob << std::endl;
711 mfem::out <<
"TMOP energy after refinement: " << tmopenergy <<
712 ", Elements: " << NEGlob << std::endl;
720 mfem::out <<
"AMR stopping criterion satisfied. Stop.\n";
738 for (
int i = 0; i < dreftable.
Size(); i++)
768 for (
int i = 0; i < integs.
Size(); i++)
781 for (
int j = 0; j < ati.
Size(); j++)
783 ati[j]->UpdateAfterMeshTopologyChange();
784 dtc = ati[j]->GetDiscreteAdaptTC();
815 for (
int i = 0; i < integs.
Size(); i++)
828 for (
int j = 0; j < ati.
Size(); j++)
830 ati[j]->ParUpdateAfterMeshTopologyChange();
831 dtc = ati[j]->GetDiscreteAdaptTC();
859 for (
int i = 0; i < mesh_->
GetNBE(); i++)
862 MFEM_VERIFY(!(
dim == 2 && attr == 3),
863 "Boundary attribute 3 must be used only for 3D meshes. "
864 "Adjust the attributes (1/2/3/4 for fixed x/y/z/all "
865 "components, rest for free nodes), or use -fix-bnd.");
866 if (attr == 1 || attr == 2 || attr == 3) { n += nd; }
867 if (attr == 4) { n += nd *
dim; }
871 for (
int i = 0; i < mesh_->
GetNBE(); i++)
877 for (
int j = 0; j < nd; j++)
878 { ess_vdofs[n++] = vdofs[j]; }
882 for (
int j = 0; j < nd; j++)
883 { ess_vdofs[n++] = vdofs[j+nd]; }
887 for (
int j = 0; j < nd; j++)
888 { ess_vdofs[n++] = vdofs[j+2*nd]; }
892 for (
int j = 0; j < vdofs.
Size(); j++)
893 { ess_vdofs[n++] = vdofs[j]; }
T Max() const
Find the maximal element in the array, using the comparison operator < for class T.
void SetSize(int nsize)
Change the logical size of the array, keep existing entries.
int Size() const
Return the logical size of the array.
int Append(const T &el)
Append element 'el' to array, resize if necessary.
Data type dense matrix using column-major storage.
void Transpose()
(*this) = (*this)^t
real_t * Data() const
Returns the matrix data array.
real_t * GetData() const
Returns the matrix data array.
FiniteElementSpace * GetTSpecFESpace()
Get the FESpace associated with tspec.
void SetTspecDataForDerefinement(FiniteElementSpace *fes)
Computes target specification data with respect to the coarse FE space.
void ResetDerefinementTspecData()
void UpdateAfterMeshTopologyChange()
Update all discrete fields based on tspec and update for AMR.
void ParUpdateAfterMeshTopologyChange()
ParFiniteElementSpace * GetTSpecParFESpace()
int GetAttribute() const
Return element's attribute.
Class FiniteElementSpace - responsible for providing FEM view of the mesh, mainly managing the set of...
const FiniteElement * GetBE(int i) const
Returns pointer to the FiniteElement in the FiniteElementCollection associated with i'th boundary fac...
DofTransformation * GetElementVDofs(int i, Array< int > &vdofs) const
Returns indices of degrees of freedom for the i'th element. The returned indices are offsets into an ...
virtual const FiniteElement * GetFE(int i) const
Returns pointer to the FiniteElement in the FiniteElementCollection associated with i'th element in t...
int GetNE() const
Returns number of elements in the mesh.
virtual void Update(bool want_transform=true)
Reflect changes in the mesh: update number of DOFs, etc. Also, calculate GridFunction transformation ...
Mesh * GetMesh() const
Returns the mesh.
const FiniteElement * GetTypicalFE() const
Return GetFE(0) if the local mesh is not empty; otherwise return a typical FE based on the Geometry t...
DofTransformation * GetBdrElementVDofs(int i, Array< int > &vdofs) const
Returns indices of degrees of freedom for i'th boundary element. The returned indices are offsets int...
Abstract class for all finite elements.
int GetDim() const
Returns the reference space dimension for the finite element.
Geometry::Type GetGeomType() const
Returns the Geometry::Type of the reference element.
int GetDof() const
Returns the number of degrees of freedom in the finite element.
Class for grid function - Vector with associated FE space.
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.
void GetElementAverages(GridFunction &avgs) const
FiniteElementSpace * FESpace()
void GetVectorValues(int i, const IntegrationRule &ir, DenseMatrix &vals, DenseMatrix &tr) const
Arbitrary order H1-conforming (continuous) finite elements.
void Set2(const real_t x1, const real_t x2)
void Set3(const real_t x1, const real_t x2, const real_t x3)
Class for an integration rule - an Array of IntegrationPoint.
IntegrationPoint & IntPoint(int i)
Returns a reference to the i-th integration point.
Arbitrary order "L2-conforming" discontinuous finite elements.
void SetOperator(const Operator &op) override
Also calls SetOperator for the preconditioner if there is one.
bool Derefined() const
Check if the mesh was de-refined.
bool Apply(Mesh &mesh)
Perform the mesh operation.
bool Stop() const
Check if STOP action is requested, e.g. stopping criterion is satisfied.
Array< int > bdr_attributes
A list of all unique boundary attributes used by the Mesh.
void GeneralRefinement(const Array< Refinement > &refinements, int nonconforming=-1, int nc_limit=0)
void FinalizeTetMesh(int generate_edges=0, int refine=0, bool fix_orientation=true)
Finalize the construction of a tetrahedral Mesh.
const FiniteElementSpace * GetNodalFESpace() const
int AddTriangle(int v1, int v2, int v3, int attr=1)
Adds a triangle to the mesh given by 3 vertices v1 through v3.
void Clear()
Clear the contents of the Mesh.
int AddVertex(real_t x, real_t y=0.0, real_t z=0.0)
int GetNE() const
Returns number of elements.
int AddTet(int v1, int v2, int v3, int v4, int attr=1)
Adds a tetrahedron to the mesh given by 4 vertices v1 through v4.
int Dimension() const
Dimension of the reference space used within the elements.
const Element * GetBdrElement(int i) const
Return pointer to the i'th boundary element object.
bool DerefineByError(Array< real_t > &elem_error, real_t threshold, int nc_limit=0, int op=1)
void GetElementTransformation(int i, IsoparametricTransformation *ElTr) const
Builds the transformation defining the i-th element in ElTr. ElTr must be allocated in advance and wi...
static Mesh MakeCartesian3D(int nx, int ny, int nz, Element::Type type, real_t sx=1.0, real_t sy=1.0, real_t sz=1.0, bool sfc_ordering=true)
Creates a mesh for the parallelepiped [0,sx]x[0,sy]x[0,sz], divided into nx*ny*nz hexahedra if type =...
void GetNodes(Vector &node_coord) const
void FinalizeTriMesh(int generate_edges=0, int refine=0, bool fix_orientation=true)
Finalize the construction of a triangular Mesh.
virtual void SetNodalFESpace(FiniteElementSpace *nfes)
int GetNBE() const
Returns number of boundary elements.
long long GetGlobalNE() const
Return the total (global) number of elements.
NCMesh * ncmesh
Optional nonconforming mesh extension.
static Mesh MakeCartesian2D(int nx, int ny, Element::Type type, bool generate_edges=false, real_t sx=1.0, real_t sy=1.0, bool sfc_ordering=true)
Creates mesh for the rectangle [0,sx]x[0,sy], divided into nx*ny quadrilaterals if type = QUADRILATER...
const CoarseFineTransformations & GetDerefinementTransforms() const
const Table & GetDerefinementTable()
int NumCols() const
Get the number of columns (size of input) of the Operator. Synonym with Width().
int NumRows() const
Get the number of rows (size of output) of the Operator. Synonym with Height().
Abstract parallel finite element space.
void Update(bool want_transform=true) override
Class for parallel grid function.
Class for parallel meshes.
A parallel extension of the NCMesh class.
void GetFineToCoarsePartitioning(const Array< int > &derefs, Array< int > &new_ranks) const
const Array< TMOP_Integrator * > & GetTMOPIntegrators() const
bool GetDerefineEnergyForIntegrator(TMOP_Integrator &tmopi, Vector &fine_energy)
void GetTMOPDerefinementEnergy(Mesh &cmesh, TMOP_Integrator &tmopi, Vector &el_energy_vec)
void RebalanceParNCMesh()
void UpdateNonlinearFormAndBC(Mesh *mesh, NonlinearForm *nlf)
TMOPRefinerEstimator * tmop_r_est
void AddGridFunctionForUpdate(GridFunction *gf)
ThresholdRefiner * tmop_r
TMOPNewtonSolver * tmopns
Array< GridFunction * > gridfuncarr
Array< ParFiniteElementSpace * > pfespacearr
TMOPDeRefinerEstimator * tmop_dr_est
Array< FiniteElementSpace * > fespacearr
TMOPHRSolver(Mesh &mesh_, NonlinearForm &nlf_, TMOPNewtonSolver &tmopns_, GridFunction &x_, bool move_bnd_, bool hradaptivity_, int mesh_poly_deg_, int amr_metric_id_, int hr_iter_=5, int h_per_r_iter_=1)
ThresholdDerefiner * tmop_dr
Array< ParGridFunction * > pgridfuncarr
void Mult(const Vector &b, Vector &x) const override
Optimizes the mesh positions given by x.
Array< IntegrationRule * > TetIntRule
real_t energy_scaling_factor
Array< IntegrationRule * > HexIntRule
void SetEnergyScalingFactor(real_t scale)
Array< IntegrationRule * > QuadIntRule
Array< IntegrationRule * > TriIntRule
IntegrationRule * SetIntRulesFromMesh(Mesh &meshsplit)
void GetTMOPRefinementEnergy(int reftype, Vector &el_energy_vec)
A TMOP integrator class based on any given TMOP_QualityMetric and TargetConstructor.
void ParUpdateAfterMeshTopologyChange()
virtual real_t GetRefinementElementEnergy(const FiniteElement &el, ElementTransformation &T, const Vector &elfun, const IntegrationRule &irule)
Computes the mean of the energies of the given element's children.
virtual real_t GetDerefinementElementEnergy(const FiniteElement &el, ElementTransformation &T, const Vector &elfun)
DiscreteAdaptTC * GetDiscreteAdaptTC() const
void UpdateAfterMeshTopologyChange()
void GetRow(int i, Array< int > &row) const
Return row i in array row (the Table must be finalized)
int Size() const
Returns the number of TYPE I elements.
De-refinement operator using an error threshold.
void Reset() override
Reset the associated estimator.
Mesh refinement operator using an error threshold.
void SetTotalErrorFraction(real_t fraction)
Set the total fraction used in the computation of the threshold. The default value is 1/2.
void Reset() override
Reset the associated estimator.
void SetSize(int s)
Resize the vector to size s.
void GetSubVector(const Array< int > &dofs, Vector &elemvect) const
Extract entries listed in dofs to the output Vector elemvect.
OutStream out(std::cout)
Global stream used by the library for standard output. Initially it uses the same std::streambuf as s...