SCOREC core
Parallel unstructured mesh tools
apf.h
Go to the documentation of this file.
1 /*
2  * Copyright 2011 Scientific Computation Research Center
3  *
4  * This work is open source software, licensed under the terms of the
5  * BSD license as described in the LICENSE file in the top-level directory.
6  */
7 
8 #ifndef APF_H
9 #define APF_H
10 
11 #include "apfMatrix.h"
12 #include "apfNew.h"
13 #include "apfDynamicArray.h"
14 
15 namespace pcu{
16  class PCU;
17 }
18 
19 #include <vector>
20 #include <map>
21 #include <limits>
22 
36 namespace apf {
37 
38 class Field;
39 class Element;
40 class Mesh;
41 class MeshEntity;
42 class MeshTag;
43 class VectorElement;
45 typedef VectorElement MeshElement;
46 class FieldShape;
47 struct Sharing;
48 template <class T> class ReductionOp;
49 template <class T> class ReductionSum;
50 
58 template <class T>
60 {
61  public:
62  /* \brief apply operation, returning a single value */
63  virtual T apply(T val1, T val2) const = 0;
64 
65  /* \brief returns a value such that apply(val, neutral_val) == val */
66  virtual T getNeutralElement() const = 0;
67 };
68 
69 template <class T>
70 class ReductionSum : public ReductionOp<T>
71 {
72  T apply(T val1, T val2) const { return val1 + val2; };
73  T getNeutralElement() const { return 0; };
74 };
75 
76 template <class T>
77 class ReductionMin : public ReductionOp<T>
78 {
79  T apply(T val1, T val2) const { return ( (val1 < val2) ? val1 : val2 ); };
80  T getNeutralElement() const { return std::numeric_limits<T>::max(); };
81 };
82 
83 template <class T>
84 class ReductionMax : public ReductionOp<T>
85 {
86  T apply(T val1, T val2) const { return ( (val1 < val2) ? val2 : val1 ); };
87  T getNeutralElement() const { return std::numeric_limits<T>::min(); };
88 };
89 
96 void destroyMesh(Mesh* m);
97 
105 MeshElement* createMeshElement(Mesh* m, MeshEntity* e);
106 
116 MeshElement* createMeshElement(Field* c, MeshEntity* e);
117 
120 MeshEntity * getMeshEntity(MeshElement * me);
121 
128 
133 enum ValueType {
144 };
145 
153 Field* createLagrangeField(Mesh* m, const char* name, int valueType, int order);
154 
165 Field* createStepField(Mesh* m, const char* name, int valueType);
166 
174 Field* createIPField(Mesh* m, const char* name, int valueType, int order);
175 
178 Field* createField(Mesh* m, const char* name, int valueType, FieldShape* shape);
179 
181 Field* createFieldOn(Mesh* m, const char* name, int valueType);
182 
189 Field* createPackedField(Mesh* m, const char* name, int components,
190  apf::FieldShape* shape = 0);
191 
194  Mesh* m,
195  const char* name,
196  int valueType,
197  int components,
198  FieldShape* shape);
199 
203 Field* cloneField(Field* f, Mesh* onto);
204 
207 Mesh* getMesh(Field* f);
208 
211 bool hasEntity(Field* f, MeshEntity* e);
212 
218 const char* getName(Field* f);
219 
222 int getValueType(Field* f);
223 
229 void destroyField(Field* f);
230 
237 void setScalar(Field* f, MeshEntity* e, int node, double value);
238 
243 double getScalar(Field* f, MeshEntity* e, int node);
244 
249 void setVector(Field* f, MeshEntity* e, int node, Vector3 const& value);
250 
253 void getVector(Field* f, MeshEntity* e, int node, Vector3& value);
254 
259 void setMatrix(Field* f, MeshEntity* e, int node, Matrix3x3 const& value);
260 
263 void getMatrix(Field* f, MeshEntity* e, int node, Matrix3x3& value);
264 
266 void setComponents(Field* f, MeshEntity* e, int node, double const* components);
267 
272 void getComponents(Field* f, MeshEntity* e, int node, double* components);
273 
284 Element* createElement(Field* f, MeshElement* e);
285 
290 Element* createElement(Field* f, MeshEntity* e);
291 
294 void destroyElement(Element* e);
295 
304 
306 MeshEntity* getMeshEntity(Element* e);
307 
313 double getScalar(Element* e, Vector3 const& param);
314 
320 void getGrad(Element* e, Vector3 const& param, Vector3& grad);
321 
327 void getVector(Element* e, Vector3 const& param, Vector3& value);
328 
334 double getDiv(Element* e, Vector3 const& param);
335 
341 void getCurl(Element* e, Vector3 const& param, Vector3& curl);
342 
352 void getVectorGrad(Element* e, Vector3 const& param, Matrix3x3& deriv);
353 
359 void getMatrix(Element* e, Vector3 const& param, Matrix3x3& value);
360 
366 void getMatrixGrad(Element* e, Vector3 const& param, Vector<27>& value);
367 
369 void getComponents(Element* e, Vector3 const& param, double* components);
370 
376 int countIntPoints(MeshElement* e, int order);
377 
384 void getIntPoint(MeshElement* e, int order, int point, Vector3& param);
385 
392 double getIntWeight(MeshElement* e, int order, int point);
393 
396 void mapLocalToGlobal(MeshElement* e, Vector3 const& local, Vector3& global);
397 
407 double getDV(MeshElement* e, Vector3 const& param);
408 
422 {
423  public:
425  Integrator(int o);
426  virtual ~Integrator();
433  void process(Mesh* m, int dim=-1);
442  virtual void inElement(MeshElement*);
449  virtual void outElement();
460  virtual void atPoint(Vector3 const& p, double w, double dV) = 0;
467  virtual void parallelReduce(pcu::PCU*);
468  protected:
469  int order;
470  int ipnode;
471 };
472 
481 double measure(MeshElement* e);
482 
487 double measure(Mesh* m, MeshEntity* e);
488 
492 
495 void getJacobian(MeshElement* e, Vector3 const& local, Matrix3x3& j);
496 
504 void getJacobianInv(MeshElement* e, Vector3 const& local, Matrix3x3& jinv);
505 
521 double computeCosAngle(Mesh* m, MeshEntity* pe, MeshEntity* e1, MeshEntity* e2,
522  const Matrix3x3& Q);
523 
524 double computeCosAngleInTri(Mesh* m, MeshEntity* tri,
525  MeshEntity* e1, MeshEntity* e2, const Matrix3x3& Q);
526 
527 double computeCosAngleInTet(Mesh* m, MeshEntity* tet,
528  MeshEntity* e1, MeshEntity* e2, const Matrix3x3& Q);
529 
530 Vector3 computeFaceNormalAtEdgeInTet(Mesh* m, MeshEntity* tet,
531  MeshEntity* face, MeshEntity* edge, Matrix3x3 Q);
532 
533 Vector3 computeFaceNormalAtVertex(Mesh* m, MeshEntity* face,
534  MeshEntity* vert, const Matrix3x3& Q);
535 
536 Vector3 computeEdgeTangentAtVertex(Mesh* m, MeshEntity* edge,
537  MeshEntity* vert, const Matrix3x3& Q);
538 
546 double computeShortestHeightInTet(Mesh* m, MeshEntity* tet,
547  const Matrix3x3& Q = Matrix3x3(1.,0.,0.,0.,1.,0.,0.,0.,1.));
548 
556 double computeLargestHeightInTet(Mesh* m, MeshEntity* tet,
557  const Matrix3x3& Q = Matrix3x3(1.,0.,0.,0.,1.,0.,0.,0.,1.));
558 
559 
567 double computeShortestHeightInTri(Mesh* m, MeshEntity* tri,
568  const Matrix3x3& Q = Matrix3x3(1.,0.,0.,0.,1.,0.,0.,0.,1.));
569 
577 double computeLargestHeightInTri(Mesh* m, MeshEntity* tri,
578  const Matrix3x3& Q = Matrix3x3(1.,0.,0.,0.,1.,0.,0.,0.,1.));
579 
580 
586 int countNodes(Element* e);
587 
590 void getScalarNodes(Element* e, NewArray<double>& values);
591 
594 void getVectorNodes(Element* e, NewArray<Vector3>& values);
595 
598 void getMatrixNodes(Element* e, NewArray<Matrix3x3>& values);
599 
602 void getShapeValues(Element* e, Vector3 const& local,
603  NewArray<double>& values);
604 
609 void getShapeGrads(Element* e, Vector3 const& local,
610  NewArray<Vector3>& grads);
611 
616 void getVectorShapeValues(Element* e, Vector3 const& local,
617  NewArray<Vector3>& values);
618 
623 void getCurlShapeValues(Element* e, Vector3 const& local,
624  NewArray<Vector3>& values);
625 
628 FieldShape* getShape(Field* f);
629 
632 int countComponents(Field* f);
633 
642 #define APF_ITERATE(t,w,i) \
643 for (t::iterator i = (w).begin(); \
644  (i) != (w).end(); ++(i))
645 
647 #define APF_CONST_ITERATE(t,w,i) \
648 for (t::const_iterator i = (w).begin(); \
649  (i) != (w).end(); ++(i))
650 
651 struct CGNSInfo
652 {
653  // cgns_bc_name
654  std::string cgnsBCSName;
655  /* tag value
656 
657  Tag value holds [0, 1] as a
658  marker to indicate mesh_entities
659  within bc group. 1="in group", 0="not in group"
660  Tags set on vertices, edges, faces, and cells
661  */
662  apf::MeshTag* bcsMarkerTag = nullptr;
663  // model dimension
664  int mdlDim = -1;
665  // model id
666  int mdlId = -1;
667 };
668 
669 //using CGNSBCMap = std::map<std::string, std::vector<std::tuple<std::string, apf::MeshTag *, int>>>;
670 using CGNSBCMap = std::map<std::string, std::vector<CGNSInfo>>;
671 void writeCGNS(const char *prefix, Mesh *m, const CGNSBCMap &cgnsBCMap);
672 
678 void writeVtkFiles(const char* prefix, Mesh* m, int cellDim = -1);
679 
686 void writeVtkFiles(const char* prefix, Mesh* m,
687  std::vector<std::string> writeFields, int cellDim = -1);
688 
692 void writeOneVtkFile(const char* prefix, Mesh* m);
693 
699 void writeASCIIVtkFiles(const char* prefix, Mesh* m);
700 
707 void writeASCIIVtkFiles(const char* prefix, Mesh* m,
708  std::vector<std::string> writeFields);
709 
714 void writeNedelecVtkFiles(const char* prefix, Mesh* m);
715 
722 void getGaussPoint(int type, int order, int point, Vector3& param);
723 
725 int countGaussPoints(int type, int order);
726 
734 double getJacobianDeterminant(Matrix3x3 const& J, int dimension);
735 
738 
744 void synchronize(Field* f, Sharing* shr = 0);
745 
752 void accumulate(Field* f, Sharing* shr = 0, bool delete_shr = false);
753 
760 void sharedReduction(Field* f, Sharing* shr, bool delete_shr,
761  const ReductionOp<double>& sum = ReductionSum<double>());
762 
766 bool isPrintable(Field* f);
767 
774 void fail(const char* why) __attribute__((noreturn));
775 
777 void freeze(Field* f);
778 
780 void unfreeze(Field* f);
781 
783 bool isFrozen(Field* f);
784 
790 double* getArrayData(Field* f);
791 
793 void zeroField(Field* f);
794 
796 struct Function
797 {
799  virtual ~Function();
806  virtual void eval(MeshEntity* e, double* result) = 0;
807 };
808 
809 /* \brief Create a Field from a user's analytic function.
810  * \details This field will use no memory, has values on all
811  * nodes, and calls the user Function for all value queries.
812  * Writing to this field does nothing.
813  * \warning if you copy the mesh with apf::convert you may want to use
814  * apf::updateUserField to update function that this field refers to. This is
815  * extremely important if the analytic function you use references user fields.
816  */
817 Field* createUserField(Mesh* m, const char* name, int valueType, FieldShape* s,
818  Function* f);
819 
820 /* \brief update the analytic function from a user field
821  * \details this field updates the apf::Function which the UserField refers to
822  */
823 void updateUserField(Field* field, Function* newFunc);
824 
829 Field* recoverGradientByVolume(Field* f);
830 
831 void copyData(Field* to, Field* from);
832 
834 void projectField(Field* to, Field* from);
835 
836 void axpy(double a, Field* x, Field* y);
837 
838 void renameField(Field* f, const char* name);
839 
847 void getBF(FieldShape* s, MeshElement* e, Vector3 const& p,
848  NewArray<double>& BF);
849 
854 void getGradBF(FieldShape* s, MeshElement* e, Vector3 const& p,
855  NewArray<Vector3>& gradBF);
856 
857 }
858 
859 #endif
The APF linear algebra matrix interface.
Describes field distribution and shape functions.
Definition: apfShape.h:92
A virtual base for user-defined integrators.
Definition: apf.h:422
virtual void outElement()
User callback: element exit.
virtual void atPoint(Vector3 const &p, double w, double dV)=0
User callback: accumulation.
virtual void inElement(MeshElement *)
User callback: element entry.
virtual void parallelReduce(pcu::PCU *)
User callback: parallel reduction.
void process(Mesh *m, int dim=-1)
Run the Integrator over the local Mesh.
void process(MeshElement *e)
Run the Integrator over a Mesh Element.
Integrator(int o)
Construct an Integrator given an order of accuracy.
convenience wrapper over apf::Matrix<3,3>
Definition: apfMatrix.h:179
Interface to a mesh part.
Definition: apfMesh.h:105
Base class for applying operations to make a Field consistent in parallel.
Definition: apf.h:60
convenience wrapper over apf::Vector<3>
Definition: apfVector.h:151
template-generic vector of N doubles
Definition: apfVector.h:47
The Parallel Contrul Unit class encapsulates parallel communication.
Definition: PCU.h:26
All APF symbols are contained in this namespace.
int countNodes(Element *e)
Returns the number of element nodes.
void writeASCIIVtkFiles(const char *prefix, Mesh *m)
Write a set of parallel VTK Unstructured Mesh files from an apf::Mesh with ASCII encoding.
Field * createStepField(Mesh *m, const char *name, int valueType)
Create an apf::Field using a step distribution.
void getJacobianInv(MeshElement *e, Vector3 const &local, Matrix3x3 &jinv)
Returns the Jacobian inverse at a local point.
void setScalar(Field *f, MeshEntity *e, int node, double value)
Set a nodal value of a scalar field.
int countIntPoints(MeshElement *e, int order)
Get the number of integration points for an element.
int countComponents(Field *f)
Count the number of scalar components in the field's value type.
double getDiv(Element *e, Vector3 const &param)
Evaluate the divergence of a vector field at a point.
void getShapeGrads(Element *e, Vector3 const &local, NewArray< Vector3 > &grads)
Returns the shape function gradients at a point.
void getGradBF(FieldShape *s, MeshElement *e, Vector3 const &p, NewArray< Vector3 > &gradBF)
Get global gradients of basis functions over a mesh element.
void getMatrixGrad(Element *e, Vector3 const &param, Vector< 27 > &value)
get the gradient of a matrix field
double getScalar(Field *f, MeshEntity *e, int node)
Get the node value of a scalar field.
VectorElement MeshElement
Mesh Elements represent the mesh coordinate vector field.
Definition: apf.h:43
double computeLargestHeightInTri(Mesh *m, MeshEntity *tri, const Matrix3x3 &Q=Matrix3x3(1., 0., 0., 0., 1., 0., 0., 0., 1.))
Returns the largest height in a tri.
MeshEntity * getMeshEntity(MeshElement *me)
Retrieve the mesh entity associated with an apf::MeshElement.
int countGaussPoints(int type, int order)
Return the number of Gaussian integration points.
void destroyField(Field *f)
Destroy an apf::Field.
void getVectorGrad(Element *e, Vector3 const &param, Matrix3x3 &deriv)
Get the gradient of a vector field w.r.t. global coordinates.
int getDimension(MeshElement *me)
Return the dimension of a MeshElement's MeshEntity.
void sharedReduction(Field *f, Sharing *shr, bool delete_shr, const ReductionOp< double > &sum=ReductionSum< double >())
Apply a reudction operator along partition boundaries.
MeshElement * getMeshElement(Element *e)
Get the Mesh Element of a Field Element.
double getIntWeight(MeshElement *e, int order, int point)
Get the weight of an integration point in an element.
void getCurl(Element *e, Vector3 const &param, Vector3 &curl)
Evaluate the curl of a vector field at a point.
void getJacobian(MeshElement *e, Vector3 const &local, Matrix3x3 &j)
Returns the Jacobian at a local point.
void getComponents(Field *f, MeshEntity *e, int node, double *components)
Copy the nodal value into an array of component values.
void getGaussPoint(int type, int order, int point, Vector3 &param)
Return the location of a gaussian integration point.
void projectField(Field *to, Field *from)
Project a field from an existing field.
Field * createLagrangeField(Mesh *m, const char *name, int valueType, int order)
Create an apf::Field using a Lagrange distribution.
void getVector(Field *f, MeshEntity *e, int node, Vector3 &value)
Get the nodal value of a vector field.
void freeze(Field *f)
Convert a Field from Tag to array storage.
double * getArrayData(Field *f)
Return the contiguous array storing this field.
void zeroField(Field *f)
Initialize all nodal values with all-zero components.
ValueType
The type of value the field stores.
Definition: apf.h:133
@ PACKED
a user-defined set of components
Definition: apf.h:141
@ VECTOR
a 3D vector value
Definition: apf.h:137
@ SCALAR
a single scalar value.
Definition: apf.h:135
@ VALUE_TYPES
placeholder used to set array sizes
Definition: apf.h:143
@ MATRIX
a 3x3 matrix
Definition: apf.h:139
Field * createPackedField(Mesh *m, const char *name, int components, apf::FieldShape *shape=0)
Create a field of N components without a tensor type.
void mapLocalToGlobal(MeshElement *e, Vector3 const &local, Vector3 &global)
Map a local coordinate to a global coordinate.
void fail(const char *why) __attribute__((noreturn))
Declare failure of code inside APF.
double getJacobianDeterminant(Matrix3x3 const &J, int dimension)
Return the Jacobian determinant or dimensional equivalent.
void getMatrixNodes(Element *e, NewArray< Matrix3x3 > &values)
Returns the element nodal values for a matrix field.
bool isPrintable(Field *f)
Checks whether a Field/Numbering/GlobalNumbering is complete and therefore printable to visualization...
double measure(MeshElement *e)
Measures the volume, area, or length of a Mesh Element.
void writeOneVtkFile(const char *prefix, Mesh *m)
Output just the .vtu file with ASCII encoding for this part.
void synchronize(Field *f, Sharing *shr=0)
Synchronize field values along partition boundary.
void unfreeze(Field *f)
Convert a Field from array to Tag storage.
void getScalarNodes(Element *e, NewArray< double > &values)
Returns the element nodal values for a scalar field.
Field * createGeneralField(Mesh *m, const char *name, int valueType, int components, FieldShape *shape)
Encompasses both packed and typed fields.
Field * createField(Mesh *m, const char *name, int valueType, FieldShape *shape)
Create a Field from any builtin or user defined FieldShape.
void getGrad(Element *e, Vector3 const &param, Vector3 &grad)
Get the gradient of a scalar field w.r.t. global coordinates.
void getMatrix(Field *f, MeshEntity *e, int node, Matrix3x3 &value)
Get the nodal value of a matrix field.
void getVectorShapeValues(Element *e, Vector3 const &local, NewArray< Vector3 > &values)
Returns the vector shape function values at a point.
void destroyMesh(Mesh *m)
Destroys an apf::Mesh.
void getIntPoint(MeshElement *e, int order, int point, Vector3 &param)
Get an integration point in an element.
int getOrder(MeshElement *e)
Returns the polynomial order of the coordinate field.
double computeCosAngle(Mesh *m, MeshEntity *pe, MeshEntity *e1, MeshEntity *e2, const Matrix3x3 &Q)
Returns the cosine of the angle between 2 entities of the parent entity.
Field * createIPField(Mesh *m, const char *name, int valueType, int order)
Create an apf::Field of integration point data.
void getVectorNodes(Element *e, NewArray< Vector3 > &values)
Returns the element nodal values for a vector field.
void setMatrix(Field *f, MeshEntity *e, int node, Matrix3x3 const &value)
Set the nodal value of a matrix field.
double computeShortestHeightInTri(Mesh *m, MeshEntity *tri, const Matrix3x3 &Q=Matrix3x3(1., 0., 0., 0., 1., 0., 0., 0., 1.))
Returns the shortest height in a tri.
const char * getName(Field *f)
Get the name of a Field.
void setComponents(Field *f, MeshEntity *e, int node, double const *components)
Set the nodal value from an array of component values.
void destroyMeshElement(MeshElement *e)
Destroys a Mesh Element.
void writeNedelecVtkFiles(const char *prefix, Mesh *m)
Output .vtk files with ASCII encoding for this part.
void setVector(Field *f, MeshEntity *e, int node, Vector3 const &value)
Set the nodal value of a vector field.
FieldShape * getShape(Field *f)
Retrieve the apf::FieldShape used by a field.
Field * createFieldOn(Mesh *m, const char *name, int valueType)
Create a field using the mesh's coordinate nodal distribution.
void destroyElement(Element *e)
Destroy a Field Element.
void writeVtkFiles(const char *prefix, Mesh *m, int cellDim=-1)
Write a set of parallel VTK Unstructured Mesh files from an apf::Mesh with binary (base64) encoding a...
void getShapeValues(Element *e, Vector3 const &local, NewArray< double > &values)
Returns the shape function values at a point.
Field * cloneField(Field *f, Mesh *onto)
Declare a copy of a field on another apf::Mesh.
double computeShortestHeightInTet(Mesh *m, MeshEntity *tet, const Matrix3x3 &Q=Matrix3x3(1., 0., 0., 0., 1., 0., 0., 0., 1.))
Returns the shortest height in a tet.
MeshElement * createMeshElement(Mesh *m, MeshEntity *e)
Creates a Mesh Element over an entity.
void getCurlShapeValues(Element *e, Vector3 const &local, NewArray< Vector3 > &values)
Returns the vector curl shape function values at a point.
void accumulate(Field *f, Sharing *shr=0, bool delete_shr=false)
Add field values along partition boundary.
double getDV(MeshElement *e, Vector3 const &param)
Get the differential volume at a point.
Field * recoverGradientByVolume(Field *f)
Compute a nodal gradient field from a nodal input field.
Mesh * getMesh(Field *f)
Retrieve the Mesh over which a Field is defined.
int getValueType(Field *f)
Retrieve the type of value a field distributes.
Element * createElement(Field *f, MeshElement *e)
Create a Field Element from a Mesh Element.
bool hasEntity(Field *f, MeshEntity *e)
Returns true iff an entity has data associate with a field.
double computeLargestHeightInTet(Mesh *m, MeshEntity *tet, const Matrix3x3 &Q=Matrix3x3(1., 0., 0., 0., 1., 0., 0., 0., 1.))
Returns the largest height in a tet.
void getBF(FieldShape *s, MeshElement *e, Vector3 const &p, NewArray< double > &BF)
Get the basis functions over a mesh element.
bool isFrozen(Field *f)
Returns true iff the Field uses array storage.
apf::Mesh2 Mesh
convenient mesh name
Definition: maMesh.h:27
Definition: PCU.h:15
User-defined Analytic Function.
Definition: apf.h:797
virtual void eval(MeshEntity *e, double *result)=0
The user's analytic function call.
virtual ~Function()
Possible user-defined cleanup.
abstract description of entity copy sharing
Definition: apfMesh.h:489