Actual source code: unstructured_1d.c

  1: #ifdef PETSC_RCS_HEADER
  2: static char vcid[] = "$Id: unstructured_1d.c,v 1.5 2000/02/01 17:02:51 knepley Exp $";
  3: #endif

  5: static char help[] = "This example deals with 1D unstructured meshes.\n\n";

  7: #include "unstructured_1d.h"

  9: /*
 10:   Here we will create a series of refined 1D unstructured meshes.
 11: */
 12: #undef  __FUNCT__
 14: int main(int argc, char **args) {
 15:   MeshContext ctx; /* Holds problem specific information */
 16:   int         ierr;

 19:   PetscInitialize(&argc, &args, 0, help);                                    CHKERRABORT(PETSC_COMM_WORLD, ierr);

 21:   MeshContextCreate(PETSC_COMM_WORLD, &ctx);                                 CHKERRABORT(PETSC_COMM_WORLD, ierr);
 22:   MeshContextRun(ctx);                                                       CHKERRABORT(PETSC_COMM_WORLD, ierr);
 23:   MeshContextDestroy(ctx);                                                   CHKERRABORT(PETSC_COMM_WORLD, ierr);

 25:   CHKMEMQ;
 26:   PetscFinalize();
 27:   return(0);
 28: }

 30: /*--------------------------------------------- MeshContext Creation -------------------------------------------------*/
 31: #undef  __FUNCT__
 33: /*@
 34:   MeshContextCreate - This function initializes the Mesh context.

 36:   Collective on MPI_Comm

 38:   Input Parameter:
 39: . comm - The communicator

 41:   Output Parameter:
 42: . mCtx - The MeshContext

 44:   Level: beginner

 46: .keywords: Mesh, context, create
 47: .seealso: MeshContextDestroy(), MeshContextPrint(), MeshContextSetup()
 48: @*/
 49: int MeshContextCreate(MPI_Comm comm, MeshContext *mCtx) {
 50:   MeshContext ctx;

 53:   /* Setup context */
 54:   PetscHeaderCreate(ctx, _MeshContext, int, PETSC_VIEWER_COOKIE, -1, "context", comm, 0, 0);
 55:   PetscLogObjectCreate(ctx);
 56:   PetscLogObjectMemory(ctx, sizeof(struct _MeshContext));

 58:   /* Initialize subobjects */
 59:   ctx->mesh = PETSC_NULL;
 60:   /* Set for vertices only */
 61:   ctx->numCorners = 2;
 62:   /* Setup domain */
 63:   ctx->geometryCtx.size[0]  = 1.0;
 64:   ctx->geometryCtx.start[0] = 0.0;
 65:   /* Setup refinement */
 66:   ctx->geometryCtx.maxArea  = 0.25;
 67:   ctx->geometryCtx.areaFunc = PointFunctionConstant;
 68:   ctx->geometryCtx.areaCtx  = PETSC_NULL;
 69:   /* Initialize problem loop */
 70:   ctx->numRefine  = 0;
 71:   ctx->numCoarsen = 0;

 73:   *mCtx = ctx;
 74:   return(0);
 75: }

 77: #undef  __FUNCT__
 79: /*@
 80:   MeshContextDestroy - This function destroys the Mesh context.

 82:   Collective on MeshContext

 84:   Input Parameter:
 85: . ctx - The MeshContext

 87:   Level: beginner

 89: .keywords: Mesh, context, destroy
 90: .seealso: MeshContextCreate()
 91: @*/
 92: int MeshContextDestroy(MeshContext ctx) {
 94:   if (--ctx->refct > 0) SETERRQ(PETSC_ERR_PLIB, "Mesh context should not be referenced more than once");
 95:   PetscLogObjectDestroy(ctx);
 96:   PetscHeaderDestroy(ctx);
 97:   return(0);
 98: }

100: /*------------------------------------------------ Mesh Creation -----------------------------------------------------*/
101: /*@
102:   MeshContextSetup - This function initializes all internal variables through options and creates the mesh.

104:   Collective on MeshContext

106:   Input Parameter:
107: . ctx - A MeshContext

109:   Options Database Keys:
110: + num_corners   - The number of nodes on an element
111: . num_refine    - The number of times to refine the mesh
112: . num_coarsen   - The number of times to coarsen the mesh
113: - mesh_max_area - The maximum area of an element after refinement

115:   Level: beginner

117: .seealso MeshContextCleanup(), MeshContextCreate()
118: @*/
119: #undef  __FUNCT__
121: int MeshContextSetup(MeshContext ctx) {
122:   PetscTruth opt;
123:   int        ierr;

126:   /* The number of corners (usually either 2 or 3) */
127:   PetscOptionsGetInt(PETSC_NULL, "-num_corners",  &ctx->numCorners,  &opt);
128:   /* The number of times to refine the mesh */
129:   PetscOptionsGetInt(PETSC_NULL, "-num_refine",  &ctx->numRefine,  &opt);
130:   /* The number of times to coarsen the mesh */
131:   PetscOptionsGetInt(PETSC_NULL, "-num_coarsen", &ctx->numCoarsen, &opt);
132:   /* Setup refinement */
133:   PetscOptionsGetReal("mesh", "-max_area", &ctx->geometryCtx.maxArea, &opt);

135:   MeshContextCreateMesh(ctx);
136:   return(0);
137: }

139: #undef  __FUNCT__
141: /*@
142:   MeshContextCreateMesh - This function creates a mesh

144:   Collective on MeshContext

146:   Input Parameter:
147: . ctx - A MeshContext

149:   Level: beginner

151: .seealso MeshContextRefineMesh(), MeshContextSetup(), MeshContextCleanup()
152: @*/
153: int MeshContextCreateMesh(MeshContext ctx) {
154:   MeshGeometryContext *geomCtx = &ctx->geometryCtx;
155:   int                  meshInfo[4], globalMeshInfo[4];
156:   char                 name[256];
157:   int                  ierr;

160:   /* Setup mesh boundary */
161:   MeshBoundary1DCreateSimple(ctx->comm, &ctx->geometryCtx, &ctx->boundaryCtx);
162:   /* Construct the mesh */
163:   MeshCreate(ctx->comm, &ctx->mesh);
164:   MeshSetDimension(ctx->mesh, 1);
165:   MeshSetPeriodicDimension(ctx->mesh, 0, geomCtx->isPeriodic[0]);
166:   MeshSetNumCorners(ctx->mesh, ctx->numCorners);
167:   MeshSetBoundary(ctx->mesh, &ctx->boundaryCtx);
168:   sprintf(name, "mesh.r%.4g", geomCtx->maxArea);
169:   PetscObjectSetName((PetscObject) ctx->mesh, name);
170:   MeshSetFromOptions(ctx->mesh);
171:   if (ctx->geometryCtx.areaCtx != PETSC_NULL) {
172:     MeshSetUserContext(ctx->mesh, ctx->geometryCtx.areaCtx);
173:   } else {
174:     MeshSetUserContext(ctx->mesh, &ctx->geometryCtx.maxArea);
175:   }
176:   MeshBoundary1DDestroy(ctx->comm, &ctx->boundaryCtx);
177:   /* Output mesh information */
178:   MeshGetInfo(ctx->mesh, &meshInfo[0], &meshInfo[1], &meshInfo[2], &meshInfo[3]);
179:   MPI_Allreduce(meshInfo, globalMeshInfo, 4, MPI_INT, MPI_SUM, ctx->comm);
180:   PetscPrintf(ctx->comm, "Vertices: %d Nodes: %d Edges: %d\n", meshInfo[0], globalMeshInfo[1], globalMeshInfo[2]);

182:   return(0);
183: }

185: #undef  __FUNCT__
187: /*@
188:   MeshContextRefineMesh - This function refines the mesh

190:   Collective on MeshContext

192:   Input Parameters:
193: . ctx - A MeshContextContext

195:   Level: beginner

197: .seealso MeshContextCoarsenMesh(), MeshContextCreateMesh(), MeshContextCleanup()
198: @*/
199: int MeshContextRefineMesh(MeshContext ctx) {
200:   MeshGeometryContext *geomCtx = &ctx->geometryCtx;
201:   Mesh                 refMesh;
202:   int                  meshInfo[4], globalMeshInfo[4];
203:   char                 name[256];
204:   int                  ierr;

207:   /* Decrease feature size */
208:   geomCtx->maxArea *= 0.5;
209:   /* Construct a refined mesh */
210:   MeshRefine(ctx->mesh, geomCtx->areaFunc, &refMesh);
211:   if (geomCtx->areaCtx != PETSC_NULL) {
212:     MeshSetUserContext(refMesh, geomCtx->areaCtx);
213:   } else {
214:     MeshSetUserContext(refMesh, &geomCtx->maxArea);
215:   }
216:   MeshSetOptionsPrefix(refMesh, "ref_");
217:   sprintf(name, "mesh.r%.4g", geomCtx->maxArea);
218:   PetscObjectSetName((PetscObject) refMesh, name);
219:   MeshSetFromOptions(refMesh);
220: #ifdef PETSC_USE_BOPT_g
221:   CHKMEMQ;
222: #endif
223:   /* Output new mesh information */
224:   MeshGetInfo(refMesh, &meshInfo[0], &meshInfo[1], &meshInfo[2], &meshInfo[3]);
225:   MPI_Allreduce(meshInfo, globalMeshInfo, 4, MPI_INT, MPI_SUM, ctx->comm);
226:   PetscPrintf(ctx->comm, "Vertices: %d Nodes: %d Edges: %d\n", meshInfo[0], globalMeshInfo[1], globalMeshInfo[2]);

228:   /* Replace old mesh with refined mesh */
229:   MeshDestroy(ctx->mesh);
230:   ctx->mesh = refMesh;
231:   return(0);
232: }

234: #undef  __FUNCT__
236: /*@
237:   MeshContextCoarsenMesh - This function coarsen the mesh

239:   Collective on MeshContext

241:   Input Parameters:
242: . ctx - A MeshContextContext

244:   Level: beginner

246: .seealso MeshContextRefineMesh(), MeshContextCreateMesh(), MeshContextCleanup()
247: @*/
248: int MeshContextCoarsenMesh(MeshContext ctx) {
250:   SETERRQ(PETSC_ERR_SUP, "No coarsening available yet");
251:   return(0);
252: }

254: #undef  __FUNCT__
256: /*@
257:   MeshContextSetup - This function destroys all internal variables including the mesh.

259:   Collective on MeshContext

261:   Input Parameter:
262: . ctx - A MeshContext

264:   Level: beginner

266: .seealso MeshContextSetup(), MeshContextCreate()
267: @*/
268: int MeshContextCleanup(MeshContext ctx) {

272:   MeshDestroy(ctx->mesh);
273:   return(0);
274: }

276: /*---------------------------------------------- Sanity Checks ------------------------------------------------------*/

278: /*---------------------------------------------- Problem Callbacks --------------------------------------------------*/

280: /*---------------------------------------------- Main Computation ---------------------------------------------------*/
281: #undef  __FUNCT__
283: int MeshContextRun(MeshContext ctx) {
284:   int loop;

288:   MeshContextSetup(ctx);

290:   for(loop = 0; loop < ctx->numRefine; loop++) {
291:     MeshContextRefineMesh(ctx);
292:   }
293:   for(loop = 0; loop < ctx->numCoarsen; loop++) {
294:     MeshContextCoarsenMesh(ctx);
295:   }

297:   MeshContextCleanup(ctx);
298:   return(0);
299: }