PetscErrorCode DMLabelPermute(DMLabel label, IS permutation, DMLabel *labelNew) { const PetscInt *perm; PetscInt numValues, numPoints, v, q; PetscErrorCode ierr; PetscFunctionBegin; ierr = DMLabelMakeAllValid_Private(label);CHKERRQ(ierr); ierr = DMLabelDuplicate(label, labelNew);CHKERRQ(ierr); ierr = DMLabelGetNumValues(*labelNew, &numValues);CHKERRQ(ierr); ierr = ISGetLocalSize(permutation, &numPoints);CHKERRQ(ierr); ierr = ISGetIndices(permutation, &perm);CHKERRQ(ierr); for (v = 0; v < numValues; ++v) { const PetscInt size = (*labelNew)->stratumSizes[v]; for (q = 0; q < size; ++q) { const PetscInt point = (*labelNew)->points[v][q]; if ((point < 0) || (point >= numPoints)) SETERRQ2(PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "Label point %D is not in [0, %D) for the remapping", point, numPoints); (*labelNew)->points[v][q] = perm[point]; } ierr = PetscSortInt(size, &(*labelNew)->points[v][0]);CHKERRQ(ierr); } ierr = ISRestoreIndices(permutation, &perm);CHKERRQ(ierr); if (label->bt) { ierr = PetscBTDestroy(&label->bt);CHKERRQ(ierr); ierr = DMLabelCreateIndex(label, label->pStart, label->pEnd);CHKERRQ(ierr); } PetscFunctionReturn(0); }
/*@C DMPlexGetLabelSize - Get the number of different integer ids in a Label Not Collective Input Parameters: + dm - The DMPlex object - name - The label name Output Parameter: . size - The number of different integer ids, or 0 if the label does not exist Level: beginner .keywords: mesh .seealso: DMLabeGetNumValues(), DMPlexSetLabelValue() @*/ PetscErrorCode DMPlexGetLabelSize(DM dm, const char name[], PetscInt *size) { DMLabel label; PetscErrorCode ierr; PetscFunctionBegin; PetscValidHeaderSpecific(dm, DM_CLASSID, 1); PetscValidCharPointer(name, 2); PetscValidPointer(size, 3); ierr = DMPlexGetLabel(dm, name, &label);CHKERRQ(ierr); *size = 0; if (!label) PetscFunctionReturn(0); ierr = DMLabelGetNumValues(label, size);CHKERRQ(ierr); PetscFunctionReturn(0); }
PetscErrorCode DMLabelConvertToSection(DMLabel label, PetscSection *section, IS *is) { IS vIS; const PetscInt *values; PetscInt *points; PetscInt nV, vS = 0, vE = 0, v, N; PetscErrorCode ierr; PetscFunctionBegin; ierr = DMLabelGetNumValues(label, &nV);CHKERRQ(ierr); ierr = DMLabelGetValueIS(label, &vIS);CHKERRQ(ierr); ierr = ISGetIndices(vIS, &values);CHKERRQ(ierr); if (nV) {vS = values[0]; vE = values[0]+1;} for (v = 1; v < nV; ++v) { vS = PetscMin(vS, values[v]); vE = PetscMax(vE, values[v]+1); } ierr = PetscSectionCreate(PETSC_COMM_SELF, section);CHKERRQ(ierr); ierr = PetscSectionSetChart(*section, vS, vE);CHKERRQ(ierr); for (v = 0; v < nV; ++v) { PetscInt n; ierr = DMLabelGetStratumSize(label, values[v], &n);CHKERRQ(ierr); ierr = PetscSectionSetDof(*section, values[v], n);CHKERRQ(ierr); } ierr = PetscSectionSetUp(*section);CHKERRQ(ierr); ierr = PetscSectionGetStorageSize(*section, &N);CHKERRQ(ierr); ierr = PetscMalloc1(N, &points);CHKERRQ(ierr); for (v = 0; v < nV; ++v) { IS is; const PetscInt *spoints; PetscInt dof, off, p; ierr = PetscSectionGetDof(*section, values[v], &dof);CHKERRQ(ierr); ierr = PetscSectionGetOffset(*section, values[v], &off);CHKERRQ(ierr); ierr = DMLabelGetStratumIS(label, values[v], &is);CHKERRQ(ierr); ierr = ISGetIndices(is, &spoints);CHKERRQ(ierr); for (p = 0; p < dof; ++p) points[off+p] = spoints[p]; ierr = ISRestoreIndices(is, &spoints);CHKERRQ(ierr); ierr = ISDestroy(&is);CHKERRQ(ierr); } ierr = ISRestoreIndices(vIS, &values);CHKERRQ(ierr); ierr = ISDestroy(&vIS);CHKERRQ(ierr); ierr = ISCreateGeneral(PETSC_COMM_SELF, N, points, PETSC_OWN_POINTER, is);CHKERRQ(ierr); PetscFunctionReturn(0); }