ENH: GeometricField: support patch groups

This commit is contained in:
mattijs
2011-12-06 17:10:01 +00:00
parent 142142b172
commit 7ad19bfba7
14 changed files with 455 additions and 155 deletions

View File

@ -248,15 +248,81 @@ GeometricBoundaryField
<< endl;
}
// Check for groups first. (using non-wild card entries of dictionaries)
forAllConstIter(dictionary, dict, iter)
{
if (iter().isDict())
{
const labelList patchIDs = bmesh_.findIndices
(
iter().keyword(),
true
);
forAll(patchIDs, i)
{
label patchi = patchIDs[i];
this->set
(
patchi,
PatchField<Type>::New
(
bmesh_[patchi],
field,
iter().dict()
)
);
}
}
}
// Check for explicit patch overrides
forAll(bmesh_, patchi)
{
if (bmesh_[patchi].type() != emptyPolyPatch::typeName)
if (bmesh_[patchi].type() == emptyPolyPatch::typeName)
{
if
(
bmesh_[patchi].type() == cyclicPolyPatch::typeName
&& !dict.found(bmesh_[patchi].name())
)
if (!this->set(patchi))
{
this->set
(
patchi,
PatchField<Type>::New
(
emptyPolyPatch::typeName,
bmesh_[patchi],
field
)
);
}
}
else
{
bool found = dict.found(bmesh_[patchi].name());
if (found)
{
this->set
(
patchi,
PatchField<Type>::New
(
bmesh_[patchi],
field,
dict.subDict(bmesh_[patchi].name())
)
);
}
}
}
// Check for any unset patches
forAll(bmesh_, patchi)
{
if (!this->set(patchi))
{
if (bmesh_[patchi].type() == cyclicPolyPatch::typeName)
{
FatalIOErrorIn
(
@ -274,30 +340,21 @@ GeometricBoundaryField
<< "Run foamUpgradeCyclics to convert mesh and fields"
<< " to split cyclics." << exit(FatalIOError);
}
this->set
(
patchi,
PatchField<Type>::New
else
{
FatalIOErrorIn
(
bmesh_[patchi],
field,
dict.subDict(bmesh_[patchi].name())
)
);
}
else
{
this->set
(
patchi,
PatchField<Type>::New
(
emptyPolyPatch::typeName,
bmesh_[patchi],
field
)
);
"GeometricField<Type, PatchField, GeoMesh>::\n"
"GeometricBoundaryField::GeometricBoundaryField\n"
"(\n"
" const BoundaryMesh&,\n"
" const DimensionedField<Type, GeoMesh>&,\n"
" const dictionary&\n"
")",
dict
) << "Cannot find patchField entry for "
<< bmesh_[patchi].name() << exit(FatalIOError);
}
}
}
}

View File

@ -32,12 +32,14 @@ Foam::patchIdentifier::patchIdentifier
(
const word& name,
const label index,
const word& physicalType
const word& physicalType,
const wordList& inGroups
)
:
name_(name),
index_(index),
physicalType_(physicalType)
physicalType_(physicalType),
inGroups_(inGroups)
{}
@ -52,6 +54,7 @@ Foam::patchIdentifier::patchIdentifier
index_(index)
{
dict.readIfPresent("physicalType", physicalType_);
dict.readIfPresent("inGroups", inGroups_);
}
@ -63,7 +66,8 @@ Foam::patchIdentifier::patchIdentifier
:
name_(p.name_),
index_(index),
physicalType_(p.physicalType_)
physicalType_(p.physicalType_),
inGroups_(p.inGroups_)
{}
@ -82,6 +86,11 @@ void Foam::patchIdentifier::write(Ostream& os) const
os.writeKeyword("physicalType") << physicalType_
<< token::END_STATEMENT << nl;
}
if (inGroups_.size())
{
os.writeKeyword("inGroups") << inGroups_
<< token::END_STATEMENT << nl;
}
}

View File

@ -35,7 +35,7 @@ SourceFiles
#ifndef patchIdentifier_H
#define patchIdentifier_H
#include "word.H"
#include "wordList.H"
#include "label.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -68,6 +68,8 @@ class patchIdentifier
//- Optional physical type
mutable word physicalType_;
//- Optional groups patch belongs to
wordList inGroups_;
public:
@ -78,7 +80,8 @@ public:
(
const word& name,
const label index,
const word& physicalType = word::null
const word& physicalType = word::null,
const wordList& inGroups = wordList()
);
//- Construct from dictionary
@ -139,6 +142,19 @@ public:
return index_;
}
//- Return the optional groups patch belongs to
const wordList& inGroups() const
{
return inGroups_;
}
//- Return the optional groups patch belongs to for modification
wordList& inGroups()
{
return inGroups_;
}
//- Write patchIdentifier as a dictionary
void write(Ostream&) const;

View File

@ -58,6 +58,16 @@ Foam::pointBoundaryMesh::pointBoundaryMesh
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
Foam::labelList Foam::pointBoundaryMesh::findIndices
(
const keyType& key,
const bool usePatchGroups
) const
{
return mesh()().boundaryMesh().findIndices(key, usePatchGroups);
}
void Foam::pointBoundaryMesh::calcGeometry()
{
PstreamBuffers pBufs(Pstream::defaultCommsType);

View File

@ -96,6 +96,9 @@ public:
return mesh_;
}
//- Find patch indices given a name
labelList findIndices(const keyType&, const bool useGroups) const;
//- Correct polyBoundaryMesh after moving points
void movePoints(const pointField&);

View File

@ -151,6 +151,7 @@ void Foam::polyBoundaryMesh::clearAddressing()
{
neighbourEdgesPtr_.clear();
patchIDPtr_.clear();
groupPatchIDsPtr_.clear();
forAll(*this, patchI)
{
@ -369,6 +370,54 @@ const Foam::labelList& Foam::polyBoundaryMesh::patchID() const
}
const Foam::HashTable<Foam::labelList, Foam::word>&
Foam::polyBoundaryMesh::groupPatchIDs() const
{
if (!groupPatchIDsPtr_.valid())
{
groupPatchIDsPtr_.reset(new HashTable<labelList, word>(10));
HashTable<labelList, word>& groupPatchIDs = groupPatchIDsPtr_();
const polyBoundaryMesh& bm = *this;
forAll(bm, patchI)
{
const wordList& groups = bm[patchI].inGroups();
forAll(groups, i)
{
const word& name = groups[i];
if (findPatchID(name) != -1)
{
WarningIn("polyBoundaryMesh::groupPatchIDs() const")
<< "Patch " << bm[patchI].name()
<< " specifies a group " << name
<< " which is also a patch name."
<< " This might give problems later on." << endl;
}
HashTable<labelList, word>::iterator iter = groupPatchIDs.find
(
name
);
if (iter != groupPatchIDs.end())
{
iter().append(patchI);
}
else
{
groupPatchIDs.insert(name, labelList(1, patchI));
}
}
}
}
return groupPatchIDsPtr_();
}
Foam::wordList Foam::polyBoundaryMesh::names() const
{
const polyPatchList& patches = *this;
@ -414,28 +463,74 @@ Foam::wordList Foam::polyBoundaryMesh::physicalTypes() const
}
Foam::labelList Foam::polyBoundaryMesh::findIndices(const keyType& key) const
Foam::labelList Foam::polyBoundaryMesh::findIndices
(
const keyType& key,
const bool usePatchGroups
) const
{
labelList indices;
DynamicList<label> indices;
if (!key.empty())
{
if (key.isPattern())
{
indices = findStrings(key, this->names());
if (usePatchGroups && groupPatchIDs().size())
{
labelHashSet indexSet(indices);
const wordList allGroupNames = groupPatchIDs().toc();
labelList groupIDs = findStrings(key, allGroupNames);
forAll(groupIDs, i)
{
const word& grpName = allGroupNames[groupIDs[i]];
const labelList& patchIDs = groupPatchIDs()[grpName];
forAll(patchIDs, j)
{
if (indexSet.insert(patchIDs[j]))
{
indices.append(patchIDs[j]);
}
}
}
}
}
else
{
indices.setSize(this->size());
label nFound = 0;
// Literal string. Special version of above to avoid
// unnecessary memory allocations
indices.setCapacity(1);
forAll(*this, i)
{
if (key == operator[](i).name())
{
indices[nFound++] = i;
indices.append(i);
break;
}
}
if (usePatchGroups && groupPatchIDs().size())
{
const HashTable<labelList, word>::const_iterator iter =
groupPatchIDs().find(key);
if (iter != groupPatchIDs().end())
{
labelHashSet indexSet(indices);
const labelList& patchIDs = iter();
forAll(patchIDs, j)
{
if (indexSet.insert(patchIDs[j]))
{
indices.append(patchIDs[j]);
}
}
}
}
indices.setSize(nFound);
}
}
@ -552,7 +647,8 @@ Foam::label Foam::polyBoundaryMesh::whichPatch(const label faceIndex) const
Foam::labelHashSet Foam::polyBoundaryMesh::patchSet
(
const UList<wordRe>& patchNames,
const bool warnNotFound
const bool warnNotFound,
const bool usePatchGroups
) const
{
const wordList allPatchNames(this->names());
@ -560,24 +656,58 @@ Foam::labelHashSet Foam::polyBoundaryMesh::patchSet
forAll(patchNames, i)
{
const word& patchName = patchNames[i];
// Treat the given patch names as wild-cards and search the set
// of all patch names for matches
labelList patchIDs = findStrings(patchNames[i], allPatchNames);
if (patchIDs.empty() && warnNotFound)
{
WarningIn
(
"polyBoundaryMesh::patchSet"
"(const wordReList&, const bool) const"
) << "Cannot find any patch names matching " << patchNames[i]
<< endl;
}
labelList patchIDs = findStrings(patchName, allPatchNames);
forAll(patchIDs, j)
{
ids.insert(patchIDs[j]);
}
if (patchIDs.empty())
{
if (usePatchGroups)
{
const wordList allGroupNames = groupPatchIDs().toc();
// Regard as group name
labelList groupIDs = findStrings(patchName, allGroupNames);
forAll(groupIDs, i)
{
const word& name = allGroupNames[groupIDs[i]];
const labelList& extraPatchIDs = groupPatchIDs()[name];
forAll(extraPatchIDs, extraI)
{
ids.insert(extraPatchIDs[extraI]);
}
}
if (groupIDs.empty() && warnNotFound)
{
WarningIn
(
"polyBoundaryMesh::patchSet"
"(const wordReList&, const bool, const bool) const"
) << "Cannot find any patch or group names matching "
<< patchName
<< endl;
}
}
else if (warnNotFound)
{
WarningIn
(
"polyBoundaryMesh::patchSet"
"(const wordReList&, const bool, const bool) const"
) << "Cannot find any patch names matching " << patchName
<< endl;
}
}
}
return ids;
@ -778,6 +908,7 @@ void Foam::polyBoundaryMesh::updateMesh()
{
neighbourEdgesPtr_.clear();
patchIDPtr_.clear();
groupPatchIDsPtr_.clear();
PstreamBuffers pBufs(Pstream::defaultCommsType);

View File

@ -70,6 +70,8 @@ class polyBoundaryMesh
mutable autoPtr<labelList> patchIDPtr_;
mutable autoPtr<HashTable<labelList, word> > groupPatchIDsPtr_;
//- Edges of neighbouring patches
mutable autoPtr<List<labelPairList> > neighbourEdgesPtr_;
@ -153,8 +155,12 @@ public:
//- Return a list of physical types
wordList physicalTypes() const;
//- Return patch indices for all matches
labelList findIndices(const keyType&) const;
//- Return patch indices for all matches. Optionally matches patchGroups
labelList findIndices
(
const keyType&,
const bool usePatchGroups = false
) const;
//- Return patch index for the first match, return -1 if not found
label findIndex(const keyType&) const;
@ -168,12 +174,17 @@ public:
//- Per boundary face label the patch index
const labelList& patchID() const;
//- Per patch group the patch indices
const HashTable<labelList, word>& groupPatchIDs() const;
//- Return the set of patch IDs corresponding to the given names
// By default warns if given names are not found.
// By default warns if given names are not found. Optionally
// matches to patchGroups as well as patchNames
labelHashSet patchSet
(
const UList<wordRe>& patchNames,
const bool warnNotFound = true
const bool warnNotFound = true,
const bool usePatchGroups = false
) const;
//- Check whether all procs have all patches and in same order. Return

View File

@ -23,8 +23,8 @@ License
\*---------------------------------------------------------------------------*/
#include "fvMesh.H"
#include "fvBoundaryMesh.H"
#include "fvMesh.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
@ -87,6 +87,16 @@ Foam::label Foam::fvBoundaryMesh::findPatchID(const word& patchName) const
}
Foam::labelList Foam::fvBoundaryMesh::findIndices
(
const keyType& key,
const bool usePatchGroups
) const
{
return mesh().boundaryMesh().findIndices(key, usePatchGroups);
}
void Foam::fvBoundaryMesh::movePoints()
{
forAll(*this, patchI)

View File

@ -109,6 +109,9 @@ public:
//- Find patch index given a name
label findPatchID(const word& patchName) const;
//- Find patch indices given a name
labelList findIndices(const keyType&, const bool useGroups) const;
//- Correct patches after moving points
void movePoints();