Actual source code: bipartite.c

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

  4: PETSC_EXTERN PetscErrorCode MatColoringCreateBipartiteGraph(MatColoring mc,PetscSF *etoc,PetscSF *etor)
  5: {
  6:   PetscInt          nentries,ncolentries,idx;
  7:   PetscInt          i,j,rs,re,cs,ce,cn;
  8:   PetscInt          *rowleaf,*colleaf,*rowdata;
  9:   PetscInt          ncol;
 10:   const PetscScalar *vcol;
 11:   const PetscInt    *icol;
 12:   const PetscInt    *coldegrees,*rowdegrees;
 13:   Mat               m = mc->mat;

 15:   MatGetOwnershipRange(m,&rs,&re);
 16:   MatGetOwnershipRangeColumn(m,&cs,&ce);
 17:   cn = ce-cs;
 18:   nentries=0;
 19:   for (i=rs;i<re;i++) {
 20:     MatGetRow(m,i,&ncol,NULL,&vcol);
 21:     for (j=0;j<ncol;j++) {
 22:       nentries++;
 23:     }
 24:     MatRestoreRow(m,i,&ncol,NULL,&vcol);
 25:   }
 26:   PetscMalloc1(nentries,&rowleaf);
 27:   PetscMalloc1(nentries,&rowdata);
 28:   idx=0;
 29:   for (i=rs;i<re;i++) {
 30:     MatGetRow(m,i,&ncol,&icol,&vcol);
 31:     for (j=0;j<ncol;j++) {
 32:       rowleaf[idx] = icol[j];
 33:       rowdata[idx] = i;
 34:       idx++;
 35:     }
 36:     MatRestoreRow(m,i,&ncol,&icol,&vcol);
 37:   }
 39:   PetscSFCreate(PetscObjectComm((PetscObject)m),etoc);
 40:   PetscSFCreate(PetscObjectComm((PetscObject)m),etor);

 42:   PetscSFSetGraphLayout(*etoc,m->cmap,nentries,NULL,PETSC_COPY_VALUES,rowleaf);
 43:   PetscSFSetFromOptions(*etoc);

 45:   /* determine the number of entries in the column matrix */
 46:   PetscLogEventBegin(MATCOLORING_Comm,*etoc,0,0,0);
 47:   PetscSFComputeDegreeBegin(*etoc,&coldegrees);
 48:   PetscSFComputeDegreeEnd(*etoc,&coldegrees);
 49:   PetscLogEventEnd(MATCOLORING_Comm,*etoc,0,0,0);
 50:   ncolentries=0;
 51:   for (i=0;i<cn;i++) {
 52:     ncolentries += coldegrees[i];
 53:   }
 54:   PetscMalloc1(ncolentries,&colleaf);

 56:   /* create the one going the other way by building the leaf set */
 57:   PetscLogEventBegin(MATCOLORING_Comm,*etoc,0,0,0);
 58:   PetscSFGatherBegin(*etoc,MPIU_INT,rowdata,colleaf);
 59:   PetscSFGatherEnd(*etoc,MPIU_INT,rowdata,colleaf);
 60:   PetscLogEventEnd(MATCOLORING_Comm,*etoc,0,0,0);

 62:   /* this one takes mat entries in *columns* to rows -- you never have to actually be able to order the leaf entries. */
 63:   PetscSFSetGraphLayout(*etor,m->rmap,ncolentries,NULL,PETSC_COPY_VALUES,colleaf);
 64:   PetscSFSetFromOptions(*etor);

 66:   PetscLogEventBegin(MATCOLORING_Comm,*etor,0,0,0);
 67:   PetscSFComputeDegreeBegin(*etor,&rowdegrees);
 68:   PetscSFComputeDegreeEnd(*etor,&rowdegrees);
 69:   PetscLogEventEnd(MATCOLORING_Comm,*etor,0,0,0);

 71:   PetscFree(rowdata);
 72:   PetscFree(rowleaf);
 73:   PetscFree(colleaf);
 74:   return 0;
 75: }