Go to the documentation of this file.
59 decompositionDict_(decompositionDict),
67 if (decompositionDict_.found(
"constraints"))
91 constraintTypes_.last()
100 decompositionDict_.found(
"preserveBaffles")
104 decompositionConstraints::preserveBafflesConstraint::typeName
116 decompositionDict_.found(
"preservePatches")
120 decompositionConstraints::preservePatchesConstraint::typeName
124 const wordReList pNames(decompositionDict_.lookup(
"preservePatches"));
134 decompositionDict_.found(
"preserveFaceZones")
138 decompositionConstraints::preserveFaceZonesConstraint::typeName
142 const wordReList zNames(decompositionDict_.lookup(
"preserveFaceZones"));
152 decompositionDict_.found(
"singleProcessorFaceSets")
156 decompositionConstraints::preserveFaceZonesConstraint::typeName
162 decompositionDict_.lookup(
"singleProcessorFaceSets")
183 word methodType(decompositionDict.
lookup(
"method"));
185 Info<<
"Selecting decompositionMethod " << methodType <<
endl;
187 dictionaryConstructorTable::iterator cstrIter =
188 dictionaryConstructorTablePtr_->find(methodType);
190 if (cstrIter == dictionaryConstructorTablePtr_->end())
193 <<
"Unknown decompositionMethod "
194 << methodType <<
nl <<
nl
195 <<
"Valid decompositionMethods are : " <<
endl
196 << dictionaryConstructorTablePtr_->sortedToc()
248 forAll(fineDistribution, i)
250 fineDistribution[i] = coarseDistribution[fineToCoarse[i]];
253 return fineDistribution;
284 return decompose(globalCellCells, cc, cWeights);
292 const label nLocalCoarse,
323 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
330 globalNeighbour[bFaceI] = globalAgglom.
toGlobal
332 agglom[faceOwner[faceI]]
342 syncTools::swapBoundaryFaceList(
mesh, globalNeighbour);
349 labelList nFacesPerCell(nLocalCoarse, 0);
351 for (
label faceI = 0; faceI <
mesh.nInternalFaces(); faceI++)
353 label own = agglom[faceOwner[faceI]];
354 label nei = agglom[faceNeighbour[faceI]];
356 nFacesPerCell[own]++;
357 nFacesPerCell[nei]++;
364 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
371 label own = agglom[faceOwner[faceI]];
373 label globalNei = globalNeighbour[bFaceI];
376 !globalAgglom.
isLocal(globalNei)
377 || globalAgglom.
toLocal(globalNei) != own
380 nFacesPerCell[own]++;
393 cellCells.
setSize(nFacesPerCell);
401 for (
label faceI = 0; faceI <
mesh.nInternalFaces(); faceI++)
403 label own = agglom[faceOwner[faceI]];
404 label nei = agglom[faceNeighbour[faceI]];
406 m[offsets[own] + nFacesPerCell[own]++] = globalAgglom.
toGlobal(nei);
407 m[offsets[nei] + nFacesPerCell[nei]++] = globalAgglom.
toGlobal(own);
415 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
422 label own = agglom[faceOwner[faceI]];
424 label globalNei = globalNeighbour[bFaceI];
428 !globalAgglom.
isLocal(globalNei)
429 || globalAgglom.
toLocal(globalNei) != own
432 m[offsets[own] + nFacesPerCell[own]++] = globalNei;
449 if (cellCells.
size() == 0)
463 for (
label i = startIndex; i < endIndex; i++)
465 if (nbrCells.
insert(cellCells.
m()[i]))
467 cellCells.
m()[newIndex++] = cellCells.
m()[i];
470 startIndex = endIndex;
471 cellCells.
offsets()[cellI+1] = newIndex;
497 const label nLocalCoarse,
529 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
536 globalNeighbour[bFaceI] = globalAgglom.
toGlobal
538 agglom[faceOwner[faceI]]
548 syncTools::swapBoundaryFaceList(
mesh, globalNeighbour);
555 labelList nFacesPerCell(nLocalCoarse, 0);
557 for (
label faceI = 0; faceI <
mesh.nInternalFaces(); faceI++)
559 label own = agglom[faceOwner[faceI]];
560 label nei = agglom[faceNeighbour[faceI]];
562 nFacesPerCell[own]++;
563 nFacesPerCell[nei]++;
570 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
577 label own = agglom[faceOwner[faceI]];
579 label globalNei = globalNeighbour[bFaceI];
582 !globalAgglom.
isLocal(globalNei)
583 || globalAgglom.
toLocal(globalNei) != own
586 nFacesPerCell[own]++;
599 cellCells.
setSize(nFacesPerCell);
600 cellCellWeights.
setSize(nFacesPerCell);
609 for (
label faceI = 0; faceI <
mesh.nInternalFaces(); faceI++)
611 label own = agglom[faceOwner[faceI]];
612 label nei = agglom[faceNeighbour[faceI]];
614 label ownIndex = offsets[own] + nFacesPerCell[own]++;
615 label neiIndex = offsets[nei] + nFacesPerCell[nei]++;
617 m[ownIndex] = globalAgglom.
toGlobal(nei);
618 w[ownIndex] =
mag(
mesh.faceAreas()[faceI]);
619 m[neiIndex] = globalAgglom.
toGlobal(own);
620 w[ownIndex] =
mag(
mesh.faceAreas()[faceI]);
628 if (pp.
coupled() && (parallel || !isA<processorPolyPatch>(pp)))
635 label own = agglom[faceOwner[faceI]];
637 label globalNei = globalNeighbour[bFaceI];
641 !globalAgglom.
isLocal(globalNei)
642 || globalAgglom.
toLocal(globalNei) != own
645 label ownIndex = offsets[own] + nFacesPerCell[own]++;
646 m[ownIndex] = globalNei;
647 w[ownIndex] =
mag(
mesh.faceAreas()[faceI]);
664 if (cellCells.
size() == 0)
678 for (
label i = startIndex; i < endIndex; i++)
680 if (nbrCells.
insert(cellCells.
m()[i]))
682 cellCells.
m()[newIndex] = cellCells.
m()[i];
683 cellCellWeights.
m()[newIndex] = cellCellWeights.
m()[i];
687 startIndex = endIndex;
688 cellCells.
offsets()[cellI+1] = newIndex;
689 cellCellWeights.
offsets()[cellI+1] = newIndex;
693 cellCellWeights.
m().
setSize(newIndex);
1093 if (nWeights > 0 && cellWeights.size() !=
mesh.nCells())
1096 <<
"Number of weights " << cellWeights.size()
1097 <<
" differs from number of cells " <<
mesh.nCells()
1103 label nProcSets = 0;
1104 forAll(specifiedProcessorFaces, setI)
1106 nProcSets += specifiedProcessorFaces[setI].
size();
1113 explicitConnections.
size(),
1118 label nUnblocked = 0;
1119 forAll(blockedFace, faceI)
1121 if (!blockedFace[faceI])
1135 if (nProcSets+nConnections+nUnblocked == 0)
1141 finalDecomp = decompose
1150 finalDecomp = decompose(
mesh,
mesh.cellCentres());
1157 Info<<
"Constrained decomposition:" <<
endl
1158 <<
" faces with same owner and neighbour processor : "
1159 << nUnblocked <<
endl
1160 <<
" baffle faces with same owner processor : "
1161 << nConnections <<
endl
1162 <<
" faces all on same processor : "
1167 regionSplit localRegion(
mesh, blockedFace, explicitConnections,
false);
1172 Info<<
"Constrained decomposition:" <<
endl
1188 forAll(localRegion, cellI)
1190 label regionI = localRegion[cellI];
1194 regionCentres[regionI] =
mesh.cellCentres()[cellI];
1205 forAll(localRegion, cellI)
1207 label regionI = localRegion[cellI];
1209 regionWeights[regionI] += cellWeights[cellI];
1214 forAll(localRegion, cellI)
1216 label regionI = localRegion[cellI];
1218 regionWeights[regionI] += 1.0;
1222 finalDecomp = decompose
1234 forAll(explicitConnections, i)
1236 const labelPair& baffle = explicitConnections[i];
1240 if (!blockedFace[f0] && !blockedFace[
f1])
1246 const label procI = finalDecomp[
mesh.faceOwner()[f0]];
1248 finalDecomp[
mesh.faceOwner()[
f1]] = procI;
1249 if (
mesh.isInternalFace(
f1))
1251 finalDecomp[
mesh.faceNeighbour()[
f1]] = procI;
1254 else if (blockedFace[f0] != blockedFace[
f1])
1257 <<
"On explicit connection between faces " << f0
1259 <<
" the two blockedFace status are not equal : "
1260 << blockedFace[f0] <<
" and " << blockedFace[
f1]
1270 if (Pstream::parRun())
1280 label nUnblocked = 0;
1281 forAll(blockedFace, faceI)
1283 if (blockedFace[faceI])
1285 faceData[faceI] =
minData(-123);
1298 forAll(blockedFace, faceI)
1300 if (!blockedFace[faceI])
1303 seedFaces[nUnblocked] = faceI;
1304 seedData[nUnblocked] =
minData(finalDecomp[own]);
1318 mesh.globalData().nTotalCells()+1
1322 forAll(finalDecomp, cellI)
1324 if (cellData[cellI].valid(deltaCalc.
data()))
1326 finalDecomp[cellI] = cellData[cellI].data();
1345 forAll(specifiedProcessorFaces, setI)
1347 const labelList& set = specifiedProcessorFaces[setI];
1349 label procI = specifiedProcessor[setI];
1354 procI = finalDecomp[
mesh.faceOwner()[set[0]]];
1367 finalDecomp[
mesh.faceOwner()[faceI]] = procI;
1368 if (
mesh.isInternalFace(faceI))
1370 finalDecomp[
mesh.faceNeighbour()[faceI]] = procI;
1378 if (debug && Pstream::parRun())
1381 syncTools::swapBoundaryCellList(
mesh, finalDecomp, nbrDecomp);
1393 label bFaceI = faceI-
mesh.nInternalFaces();
1395 if (!blockedFace[faceI])
1397 label ownProc = finalDecomp[own];
1398 label nbrProc = nbrDecomp[bFaceI];
1399 if (ownProc != nbrProc)
1402 <<
"patch:" << pp.
name()
1403 <<
" face:" << faceI
1404 <<
" at:" <<
mesh.faceCentres()[faceI]
1405 <<
" ownProc:" << ownProc
1406 <<
" nbrProc:" << nbrProc
1432 specifiedProcessorFaces.
clear();
1433 explicitConnections.
clear();
1435 forAll(constraints_, constraintI)
1437 constraints_[constraintI].add
1441 specifiedProcessorFaces,
1459 forAll(constraints_, constraintI)
1461 constraints_[constraintI].apply
1465 specifiedProcessorFaces,
1467 explicitConnections,
1490 specifiedProcessorFaces,
1504 specifiedProcessorFaces,
1516 specifiedProcessorFaces,
1518 explicitConnections,
const List< label > & offsets() const
Return the offset table (= size()+1)
const List< T > & m() const
Return the packed matrix of data.
static void calcCellCells(const polyMesh &mesh, const labelList &agglom, const label nLocalCoarse, const bool global, CompactListList< label > &cellCells)
Helper: determine (local or global) cellCells from mesh.
For use with FaceCellWave. Transports minimum passive data.
volScalarField w(IOobject("w", runTime.timeName(), mesh, IOobject::READ_IF_PRESENT, IOobject::NO_WRITE), mesh, dimensionedScalar("w", dimensionSet(0, 0, 0, 0, 0, 0, 0), 0.0))
A class for handling words, derived from string.
autoPtr< BasicCompressibleTurbulenceModel > New(const volScalarField &rho, const volVectorField &U, const surfaceScalarField &phi, const typename BasicCompressibleTurbulenceModel::transportModel &transport, const word &propertiesName)
T returnReduce(const T &Value, const BinaryOp &bop, const int tag=Pstream::msgType(), const label comm=UPstream::worldComm)
#define forAll(list, i)
Loop across all elements in list.
label findIndex(const ListType &, typename ListType::const_reference, const label start=0)
Find first occurence of given element and return index,.
static autoPtr< decompositionMethod > New(const dictionary &decompositionDict)
Return a reference to the selected decomposition method.
defineRunTimeSelectionTable(reactionRateFlameArea, dictionary)
A packed storage unstructured matrix of objects of type <T> using an offset table for access.
virtual bool coupled() const
Return true if this patch is geometrically coupled (i.e. faces and.
ITstream & lookup(const word &, bool recursive=false, bool patternMatch=true) const
Find and return an entry data stream.
const Type & first() const
Return first.
const TrackingData & data() const
Additional data to be passed into container.
bool isLocal(const label i) const
Is on local processor.
Ostream & endl(Ostream &os)
Add newline and flush stream.
decompositionMethod(const decompositionMethod &)
Disallow default bitwise copy construct and assignment.
dimensioned< scalar > mag(const dimensioned< Type > &)
Mesh consisting of general polyhedral cells.
forAllConstIter(PtrDictionary< phaseModel >, mixture.phases(), phase)
Info<< "Finished reading KIVA file"<< endl;cellShapeList cellShapes(nPoints);labelList cellZoning(nPoints, -1);const cellModel &hex=*(cellModeller::lookup("hex"));labelList hexLabels(8);label activeCells=0;labelList pointMap(nPoints);forAll(pointMap, i){ pointMap[i]=i;}for(label i=0;i< nPoints;i++){ if(f[i] > 0.0) { hexLabels[0]=i;hexLabels[1]=i1tab[i];hexLabels[2]=i3tab[i1tab[i]];hexLabels[3]=i3tab[i];hexLabels[4]=i8tab[i];hexLabels[5]=i1tab[i8tab[i]];hexLabels[6]=i3tab[i1tab[i8tab[i]]];hexLabels[7]=i3tab[i8tab[i]];cellShapes[activeCells]=cellShape(hex, hexLabels);edgeList edges=cellShapes[activeCells].edges();forAll(edges, ei) { if(edges[ei].mag(points)< SMALL) { label start=pointMap[edges[ei].start()];while(start !=pointMap[start]) { start=pointMap[start];} label end=pointMap[edges[ei].end()];while(end !=pointMap[end]) { end=pointMap[end];} label minLabel=min(start, end);pointMap[start]=pointMap[end]=minLabel;} } cellZoning[activeCells]=idreg[i];activeCells++;}}cellShapes.setSize(activeCells);cellZoning.setSize(activeCells);forAll(cellShapes, celli){ cellShape &cs=cellShapes[celli];forAll(cs, i) { cs[i]=pointMap[cs[i]];} cs.collapse();}label bcIDs[11]={-1, 0, 2, 4, -1, 5, -1, 6, 7, 8, 9};const label nBCs=12;const word *kivaPatchTypes[nBCs]={ &wallPolyPatch::typeName, &wallPolyPatch::typeName, &wallPolyPatch::typeName, &wallPolyPatch::typeName, &symmetryPolyPatch::typeName, &wedgePolyPatch::typeName, &polyPatch::typeName, &polyPatch::typeName, &polyPatch::typeName, &polyPatch::typeName, &symmetryPolyPatch::typeName, &oldCyclicPolyPatch::typeName};enum patchTypeNames{ PISTON, VALVE, LINER, CYLINDERHEAD, AXIS, WEDGE, INFLOW, OUTFLOW, PRESIN, PRESOUT, SYMMETRYPLANE, CYCLIC};const char *kivaPatchNames[nBCs]={ "piston", "valve", "liner", "cylinderHead", "axis", "wedge", "inflow", "outflow", "presin", "presout", "symmetryPlane", "cyclic"};List< SLList< face > > pFaces[nBCs]
void reduce(const List< UPstream::commsStruct > &comms, T &Value, const BinaryOp &bop, const int tag, const label comm)
intWM_LABEL_SIZE_t label
A label is an int32_t or int64_t as specified by the pre-processor macro WM_LABEL_SIZE.
Pre-declare SubField and related Field type.
void append(const T &)
Append an element at the end of the list.
A patch is a list of labels that address the faces in the global face list.
const Type & second() const
Return second.
This class separates the mesh into distinct unconnected regions, each of which is then given a label ...
A templated 1D list of pointers to objects of type <T>, where the size of the array is known and used...
void setConstraints(const polyMesh &mesh, boolList &blockedFace, PtrList< labelList > &specifiedProcessorFaces, labelList &specifiedProcessor, List< labelPair > &explicitConnections)
Helper: extract constraints:
A list of keyword definitions, which are a keyword followed by any number of values (e....
void clear()
Clear the PtrList, i.e. set size to zero deleting all the.
Calculates a unique integer (label so might not have enough room - 2G max) for processor + local inde...
label start() const
Return start label of this patch in the polyMesh face list.
void setSize(const label nRows)
Reset size of CompactListList.
errorManipArg< error, int > exit(error &err, const int errNo=1)
dimensioned< Type > max(const dimensioned< Type > &, const dimensioned< Type > &)
void setSize(const label)
Reset size of List.
Wave propagation of information through grid. Every iteration information goes through one layer of c...
label toLocal(const label i) const
From global to local on current processor.
virtual labelList decompose(const pointField &points, const scalarField &pointWeights)
Return for every coordinate the wanted processor number.
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
An ordered pair of two objects of type <T> with first() and second() elements.
void clear()
Clear all entries from table.
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
void clear()
Clear the list, i.e. set size to zero.
label size() const
Return the number of elements in the PtrList.
label size() const
Return the primary size, i.e. the number of rows.
bool insert(const Key &key)
Insert a new entry.
void applyConstraints(const polyMesh &mesh, const boolList &blockedFace, const PtrList< labelList > &specifiedProcessorFaces, const labelList &specifiedProcessor, const List< labelPair > &explicitConnections, labelList &finalDecomp)
Helper: apply constraints to a decomposition. This gives.
label readLabel(Istream &is)
A face is a list of labels corresponding to mesh vertices.
void size(const label)
Override size to be inconsistent with allocated storage.
const dictionary & subDict(const word &) const
Find and return a sub-dictionary.
defineTypeNameAndDebug(combustionModel, 0)
const word & name() const
Return name.
label nLocalRegions() const
Return local number of regions.
label toGlobal(const label i) const
From local to global.