Actual source code: coarsen.c

petsc-3.14.0 2020-09-29
Report Typos and Errors

  2: #include <petsc/private/matimpl.h>

  4: /* Logging support */
  5: PetscClassId MAT_COARSEN_CLASSID;

  7: PetscFunctionList MatCoarsenList              = NULL;
  8: PetscBool         MatCoarsenRegisterAllCalled = PETSC_FALSE;

 10: /*@C
 11:    MatCoarsenRegister - Adds a new sparse matrix coarsening algorithm to the matrix package.

 13:    Logically Collective

 15:    Input Parameters:
 16: +  sname - name of coarsen (for example MATCOARSENMIS)
 17: -  function - function pointer that creates the coarsen type

 19:    Level: developer

 21:    Sample usage:
 22: .vb
 23:    MatCoarsenRegister("my_agg",MyAggCreate);
 24: .ve

 26:    Then, your aggregator can be chosen with the procedural interface via
 27: $     MatCoarsenSetType(agg,"my_agg")
 28:    or at runtime via the option
 29: $     -mat_coarsen_type my_agg

 31: .seealso: MatCoarsenRegisterDestroy(), MatCoarsenRegisterAll()
 32: @*/
 33: PetscErrorCode  MatCoarsenRegister(const char sname[],PetscErrorCode (*function)(MatCoarsen))
 34: {

 38:   MatInitializePackage();
 39:   PetscFunctionListAdd(&MatCoarsenList,sname,function);
 40:   return(0);
 41: }

 43: /*@C
 44:    MatCoarsenGetType - Gets the Coarsen method type and name (as a string)
 45:         from the coarsen context.

 47:    Not collective

 49:    Input Parameter:
 50: .  coarsen - the coarsen context

 52:    Output Parameter:
 53: .  type - coarsener type

 55:    Level: advanced

 57:    Not Collective

 59: .seealso: MatCoarsenCreate(), MatCoarsenType, MatCoarsenSetType()
 60: @*/
 61: PetscErrorCode  MatCoarsenGetType(MatCoarsen coarsen,MatCoarsenType *type)
 62: {
 66:   *type = ((PetscObject)coarsen)->type_name;
 67:   return(0);
 68: }

 70: /*@
 71:    MatCoarsenApply - Gets a coarsen for a matrix.

 73:    Collective on MatCoarsen

 75:    Input Parameter:
 76: .   coarsen - the coarsen

 78:    Options Database Keys:
 79:    To specify the coarsen through the options database, use one of
 80:    the following
 81: $    -mat_coarsen_type mis
 82:    To see the coarsen result
 83: $    -mat_coarsen_view

 85:    Level: advanced

 87:    Notes:
 88:     Use MatCoarsenGetData() to access the results of the coarsening

 90:    The user can define additional coarsens; see MatCoarsenRegister().

 92: .seealso:  MatCoarsenRegister(), MatCoarsenCreate(),
 93:            MatCoarsenDestroy(), MatCoarsenSetAdjacency(), ISCoarsenToNumbering(),
 94:            ISCoarsenCount(), MatCoarsenGetData()
 95: @*/
 96: PetscErrorCode  MatCoarsenApply(MatCoarsen coarser)
 97: {

103:   if (!coarser->graph->assembled) SETERRQ(PetscObjectComm((PetscObject)coarser),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
104:   if (coarser->graph->factortype) SETERRQ(PetscObjectComm((PetscObject)coarser),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
105:   if (!coarser->ops->apply) SETERRQ(PetscObjectComm((PetscObject)coarser),PETSC_ERR_ARG_WRONGSTATE,"Must set type with MatCoarsenSetFromOptions() or MatCoarsenSetType()");
106:   PetscLogEventBegin(MAT_Coarsen,coarser,0,0,0);
107:   (*coarser->ops->apply)(coarser);
108:   PetscLogEventEnd(MAT_Coarsen,coarser,0,0,0);
109:   return(0);
110: }

112: /*@
113:    MatCoarsenSetAdjacency - Sets the adjacency graph (matrix) of the thing to be coarsened.

115:    Collective on MatCoarsen

117:    Input Parameters:
118: +  agg - the coarsen context
119: -  adj - the adjacency matrix

121:    Level: advanced

123: .seealso: MatCoarsenCreate(), MatCoarsenApply()
124: @*/
125: PetscErrorCode  MatCoarsenSetAdjacency(MatCoarsen agg, Mat adj)
126: {
130:   agg->graph = adj;
131:   return(0);
132: }

134: /*@
135:    MatCoarsenSetStrictAggs - Set whether to keep strict (non overlapping) aggregates in the linked list of aggregates for a coarsen context

137:    Logically Collective on MatCoarsen

139:    Input Parameters:
140: +  agg - the coarsen context
141: -  str - PETSC_TRUE keep strict aggregates, PETSC_FALSE allow overlap
142:    Level: advanced

144: .seealso: MatCoarsenCreate()
145: @*/
146: PetscErrorCode MatCoarsenSetStrictAggs(MatCoarsen agg, PetscBool str)
147: {
150:   agg->strict_aggs = str;
151:   return(0);
152: }

154: /*@
155:    MatCoarsenDestroy - Destroys the coarsen context.

157:    Collective on MatCoarsen

159:    Input Parameters:
160: .  agg - the coarsen context

162:    Level: advanced

164: .seealso: MatCoarsenCreate()
165: @*/
166: PetscErrorCode  MatCoarsenDestroy(MatCoarsen *agg)
167: {

171:   if (!*agg) return(0);
173:   if (--((PetscObject)(*agg))->refct > 0) {*agg = NULL; return(0);}

175:   if ((*agg)->ops->destroy) {
176:     (*(*agg)->ops->destroy)((*agg));
177:   }

179:   if ((*agg)->agg_lists) {
180:     PetscCDDestroy((*agg)->agg_lists);
181:   }

183:   PetscHeaderDestroy(agg);
184:   return(0);
185: }

187: /*@
188:    MatCoarsenCreate - Creates a coarsen context.

190:    Collective

192:    Input Parameter:
193: .   comm - MPI communicator

195:    Output Parameter:
196: .  newcrs - location to put the context

198:    Level: advanced

200: .seealso: MatCoarsenSetType(), MatCoarsenApply(), MatCoarsenDestroy(),
201:           MatCoarsenSetAdjacency(), MatCoarsenGetData()

203: @*/
204: PetscErrorCode  MatCoarsenCreate(MPI_Comm comm, MatCoarsen *newcrs)
205: {
206:   MatCoarsen     agg;

210:   *newcrs = NULL;

212:   MatInitializePackage();
213:   PetscHeaderCreate(agg, MAT_COARSEN_CLASSID,"MatCoarsen","Matrix/graph coarsen", "MatCoarsen", comm, MatCoarsenDestroy, MatCoarsenView);

215:   *newcrs = agg;
216:   return(0);
217: }

219: /*@C
220:    MatCoarsenViewFromOptions - View from Options

222:    Collective on MatCoarsen

224:    Input Parameters:
225: +  A - the coarsen context
226: .  obj - Optional object
227: -  name - command line option

229:    Level: intermediate
230: .seealso:  MatCoarsen, MatCoarsenView, PetscObjectViewFromOptions(), MatCoarsenCreate()
231: @*/
232: PetscErrorCode  MatCoarsenViewFromOptions(MatCoarsen A,PetscObject obj,const char name[])
233: {

238:   PetscObjectViewFromOptions((PetscObject)A,obj,name);
239:   return(0);
240: }

242: /*@C
243:    MatCoarsenView - Prints the coarsen data structure.

245:    Collective on MatCoarsen

247:    Input Parameters:
248: +  agg - the coarsen context
249: -  viewer - optional visualization context

251:    Level: advanced

253:    Note:
254:    The available visualization contexts include
255: +     PETSC_VIEWER_STDOUT_SELF - standard output (default)
256: -     PETSC_VIEWER_STDOUT_WORLD - synchronized standard
257:          output where only the first processor opens
258:          the file.  All other processors send their
259:          data to the first processor to print.

261:    The user can open alternative visualization contexts with
262: .     PetscViewerASCIIOpen() - output to a specified file

264: .seealso: PetscViewerASCIIOpen()
265: @*/
266: PetscErrorCode  MatCoarsenView(MatCoarsen agg,PetscViewer viewer)
267: {
269:   PetscBool      iascii;

273:   if (!viewer) {
274:     PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)agg),&viewer);
275:   }

279:   PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);
280:   PetscObjectPrintClassNamePrefixType((PetscObject)agg,viewer);
281:   if (agg->ops->view) {
282:     PetscViewerASCIIPushTab(viewer);
283:     (*agg->ops->view)(agg,viewer);
284:     PetscViewerASCIIPopTab(viewer);
285:   }
286:   return(0);
287: }

289: /*@C
290:    MatCoarsenSetType - Sets the type of aggregator to use

292:    Collective on MatCoarsen

294:    Input Parameter:
295: +  coarser - the coarsen context.
296: -  type - a known coarsening method

298:    Options Database Command:
299: $  -mat_coarsen_type  <type>
300: $      Use -help for a list of available methods
301: $      (for instance, mis)

303:    Level: advanced

305: .seealso: MatCoarsenCreate(), MatCoarsenApply(), MatCoarsenType, MatCoarsenGetType()

307: @*/
308: PetscErrorCode  MatCoarsenSetType(MatCoarsen coarser, MatCoarsenType type)
309: {
310:   PetscErrorCode ierr,(*r)(MatCoarsen);
311:   PetscBool      match;


317:   PetscObjectTypeCompare((PetscObject)coarser,type,&match);
318:   if (match) return(0);

320:   if (coarser->setupcalled) {
321:      (*coarser->ops->destroy)(coarser);

323:     coarser->ops->destroy = NULL;
324:     coarser->subctx       = NULL;
325:     coarser->setupcalled  = 0;
326:   }

328:    PetscFunctionListFind(MatCoarsenList,type,&r);

330:   if (!r) SETERRQ1(PetscObjectComm((PetscObject)coarser),PETSC_ERR_ARG_UNKNOWN_TYPE,"Unknown coarsen type %s",type);

332:   coarser->ops->destroy = (PetscErrorCode (*)(MatCoarsen)) 0;
333:   coarser->ops->view    = (PetscErrorCode (*)(MatCoarsen,PetscViewer)) 0;

335:   (*r)(coarser);

337:   PetscFree(((PetscObject)coarser)->type_name);
338:   PetscStrallocpy(type,&((PetscObject)coarser)->type_name);
339:   return(0);
340: }

342: /*@C
343:    MatCoarsenSetGreedyOrdering - Sets the ordering of the vertices to use with a greedy coarsening method

345:    Logically Collective on Coarsen

347:    Input Parameters:
348: +  coarser - the coarsen context
349: -  perm - vertex ordering of (greedy) algorithm

351:    Level: advanced

353:    Notes:
354:       The IS weights is freed by PETSc, so user has given this to us

356: .seealso: MatCoarsenCreate(), MatCoarsenSetType()
357: @*/
358: PetscErrorCode MatCoarsenSetGreedyOrdering(MatCoarsen coarser, const IS perm)
359: {
362:   coarser->perm = perm;
363:   return(0);
364: }

366: /*@C
367:    MatCoarsenGetData - Gets the weights for vertices for a coarsen.

369:    Logically Collective on Coarsen

371:    Input Parameter:
372: .  coarser - the coarsen context

374:    Output Parameter:
375: .  llist - linked list of aggregates

377:    Level: advanced

379: .seealso: MatCoarsenCreate(), MatCoarsenSetType()
380: @*/
381: PetscErrorCode MatCoarsenGetData(MatCoarsen coarser, PetscCoarsenData **llist)
382: {
385:   if (!coarser->agg_lists) SETERRQ(PetscObjectComm((PetscObject)coarser),PETSC_ERR_ARG_WRONGSTATE,"No linked list - generate it or call ApplyCoarsen");
386:   *llist             = coarser->agg_lists;
387:   coarser->agg_lists = NULL; /* giving up ownership */
388:   return(0);
389: }

391: /*@
392:    MatCoarsenSetFromOptions - Sets various coarsen options from the
393:         options database.

395:    Collective on MatCoarsen

397:    Input Parameter:
398: .  coarser - the coarsen context.

400:    Options Database Command:
401: $  -mat_coarsen_type  <type>
402: $      Use -help for a list of available methods
403: $      (for instance, mis)

405:    Level: advanced

407: @*/
408: PetscErrorCode MatCoarsenSetFromOptions(MatCoarsen coarser)
409: {
411:   PetscBool      flag;
412:   char           type[256];
413:   const char     *def;

416:   PetscObjectOptionsBegin((PetscObject)coarser);
417:   if (!((PetscObject)coarser)->type_name) {
418:     def = MATCOARSENMIS;
419:   } else {
420:     def = ((PetscObject)coarser)->type_name;
421:   }

423:   PetscOptionsFList("-mat_coarsen_type","Type of aggregator","MatCoarsenSetType",MatCoarsenList,def,type,256,&flag);
424:   if (flag) {
425:     MatCoarsenSetType(coarser,type);
426:   }
427:   /*
428:    Set the type if it was never set.
429:    */
430:   if (!((PetscObject)coarser)->type_name) {
431:     MatCoarsenSetType(coarser,def);
432:   }

434:   if (coarser->ops->setfromoptions) {
435:     (*coarser->ops->setfromoptions)(PetscOptionsObject,coarser);
436:   }
437:   PetscOptionsEnd();
438:   MatCoarsenViewFromOptions(coarser,NULL,"-mat_coarsen_view");
439:   return(0);
440: }