Commit 84e2df49 authored by Mark Olesen's avatar Mark Olesen
Browse files

ENH: added ZoneMesh indices(), selection() with wordRes matcher

- rationalized code dealing with extraction of name or indices from
  coordinateSystems, polyBoundaryMesh, faBoundaryMesh, fvBoundaryMesh,
  ZoneMesh to use internal implementations that allow direct
  searching/matching without building an intermediate list of names.

- simpler and more efficient handling of patch group matching.
parent c0c59b9a
......@@ -88,10 +88,9 @@ int main(int argc, char *argv[])
forAllConstIter(dictionary, agglomDict, iter)
{
labelList patchids = boundary.findIndices(iter().keyword());
forAll(patchids, i)
labelList patchids = boundary.indices(iter().keyword());
for (const label patchi : patchids)
{
label patchi = patchids[i];
const polyPatch& pp = boundary[patchi];
if (!pp.coupled())
......
......@@ -338,12 +338,11 @@ int main(int argc, char *argv[])
const polyBoundaryMesh& patches = mesh.boundaryMesh();
const polyBoundaryMesh& coarsePatches = coarseMesh.boundaryMesh();
labelList viewFactorsPatches(patches.findIndices(viewFactorWall));
forAll(viewFactorsPatches, i)
labelList viewFactorsPatches(patches.indices(viewFactorWall));
for (const label patchi : viewFactorsPatches)
{
label patchI = viewFactorsPatches[i];
nCoarseFaces += coarsePatches[patchI].size();
nFineFaces += patches[patchI].size();
nCoarseFaces += coarsePatches[patchi].size();
nFineFaces += patches[patchi].size();
}
// total number of coarse faces
......@@ -370,10 +369,8 @@ int main(int argc, char *argv[])
DynamicList<label> localAgg(nCoarseFaces);
labelHashSet includePatches;
forAll(viewFactorsPatches, i)
for (const label patchID : viewFactorsPatches)
{
const label patchID = viewFactorsPatches[i];
const polyPatch& pp = patches[patchID];
const labelList& agglom = finalAgglom[patchID];
......
......@@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd.
\\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
......@@ -55,7 +55,7 @@ readField
{
if (iter().isDict() && !iter().keyword().isPattern())
{
label patchi = bmesh_.findPatchID(iter().keyword());
const label patchi = bmesh_.findPatchID(iter().keyword());
if (patchi != -1)
{
......@@ -98,16 +98,11 @@ readField
if (e.isDict() && !e.keyword().isPattern())
{
const labelList patchIDs = bmesh_.findIndices
(
e.keyword(),
true // use patchGroups
);
const labelList patchIds =
bmesh_.indices(e.keyword(), true); // use patchGroups
forAll(patchIDs, i)
for (const label patchi : patchIds)
{
label patchi = patchIDs[i];
if (!this->set(patchi))
{
this->set
......
......@@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation |
\\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
......@@ -44,9 +44,8 @@ Description
namespace Foam
{
// Forward declaration of friend functions and operators
// Forward declarations
template<class> class DynamicID;
template<class ObjectType>
Ostream& operator<<(Ostream&, const DynamicID<ObjectType>&);
......@@ -74,18 +73,19 @@ public:
DynamicID(const keyType& key, const ObjectType& obj)
:
key_(key),
indices_(obj.findIndices(key_))
indices_(obj.indices(key_))
{}
//- Construct from Istream
DynamicID(Istream& is, const ObjectType& obj)
:
key_(is),
indices_(obj.findIndices(key_))
indices_(obj.indices(key_))
{}
// Destructor - default
//- Destructor
~DynamicID() = default;
// Member Functions
......@@ -107,7 +107,7 @@ public:
//- Return index of first matching zone
label index() const
{
return indices_.empty() ? -1 : indices_[0];
return indices_.empty() ? -1 : indices_.first();
}
//- Has the zone been found
......@@ -122,7 +122,7 @@ public:
//- Update
void update(const ObjectType& obj)
{
indices_ = obj.findIndices(key_);
indices_ = obj.indices(key_);
}
......
......@@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
\\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
......@@ -58,19 +58,20 @@ Foam::pointBoundaryMesh::pointBoundaryMesh
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
Foam::label Foam::pointBoundaryMesh::findPatchID(const word& patchName) const
{
return mesh()().boundaryMesh().findPatchID(patchName);
}
Foam::labelList Foam::pointBoundaryMesh::findIndices
Foam::labelList Foam::pointBoundaryMesh::indices
(
const keyType& key,
const bool usePatchGroups
const bool useGroups
) const
{
return mesh()().boundaryMesh().findIndices(key, usePatchGroups);
return mesh()().boundaryMesh().indices(key, useGroups);
}
Foam::label Foam::pointBoundaryMesh::findPatchID(const word& patchName) const
{
return mesh()().boundaryMesh().findPatchID(patchName);
}
......
......@@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2013 OpenFOAM Foundation
\\/ M anipulation |
\\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
......@@ -42,7 +42,7 @@ SourceFiles
namespace Foam
{
// Forward declaration of classes
// Forward declarations
class pointMesh;
class polyBoundaryMesh;
......@@ -62,7 +62,7 @@ class pointBoundaryMesh
// Private Member Functions
//- Calculate the geometry for the patches (transformation tensors etc.)
//- Calculate geometry for the patches (transformation tensors etc.)
void calcGeometry();
//- No copy construct
......@@ -88,7 +88,7 @@ public:
);
// Member functions
// Member Functions
//- Return the mesh reference
const pointMesh& mesh() const
......@@ -96,17 +96,27 @@ public:
return mesh_;
}
//- Find patch indices given a name
labelList indices(const keyType& key, const bool useGroups) const;
//- 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 polyBoundaryMesh after moving points
void movePoints(const pointField&);
//- Correct polyBoundaryMesh after topology update
void updateMesh();
// Housekeeping
//- Identical to the indices() method (AUG-2018)
labelList findIndices(const keyType& key, const bool useGroups) const
{
return indices(key, useGroups);
}
};
......
......@@ -40,6 +40,81 @@ namespace Foam
defineTypeNameAndDebug(polyBoundaryMesh, 0);
}
// * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
namespace Foam
{
// Templated implementation for types(), names(), etc - file-scope
template<class ListType, class GetOp>
static ListType getMethodImpl
(
const polyPatchList& list,
const GetOp& getop
)
{
const label len = list.size();
ListType output(len);
for (label i = 0; i < len; ++i)
{
output[i] = getop(list[i]);
}
return output;
}
// Templated implementation for indices() - file-scope
template<class UnaryMatchPredicate>
static labelList indicesImpl
(
const polyPatchList& list,
const UnaryMatchPredicate& matcher
)
{
const label len = list.size();
labelList output(len);
label count = 0;
for (label i = 0; i < len; ++i)
{
if (matcher(list[i].name()))
{
output[count++] = i;
}
}
output.resize(count);
return output;
}
// Templated implementation for findIndex() - file-scope
template<class UnaryMatchPredicate>
label findIndexImpl
(
const polyPatchList& list,
const UnaryMatchPredicate& matcher
)
{
const label len = list.size();
for (label i = 0; i < len; ++i)
{
if (matcher(list[i].name()))
{
return i;
}
}
return -1;
}
} // End namespace Foam
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
......@@ -169,9 +244,11 @@ Foam::polyBoundaryMesh::polyBoundaryMesh
void Foam::polyBoundaryMesh::clearGeom()
{
forAll(*this, patchi)
polyPatchList& patches = *this;
for (polyPatch& p : patches)
{
operator[](patchi).clearGeom();
p.clearGeom();
}
}
......@@ -182,9 +259,11 @@ void Foam::polyBoundaryMesh::clearAddressing()
patchIDPtr_.clear();
groupPatchIDsPtr_.clear();
forAll(*this, patchi)
polyPatchList& patches = *this;
for (polyPatch& p : patches)
{
operator[](patchi).clearAddressing();
p.clearAddressing();
}
}
......@@ -402,11 +481,11 @@ Foam::polyBoundaryMesh::groupPatchIDs() const
groupPatchIDsPtr_.reset(new HashTable<labelList>(16));
auto& groupPatchIDs = *groupPatchIDsPtr_;
const polyBoundaryMesh& bm = *this;
const polyBoundaryMesh& patches = *this;
forAll(bm, patchi)
forAll(patches, patchi)
{
const wordList& groups = bm[patchi].inGroups();
const wordList& groups = patches[patchi].inGroups();
for (const word& groupName : groups)
{
......@@ -424,12 +503,12 @@ Foam::polyBoundaryMesh::groupPatchIDs() const
}
// Remove patch names from patchGroups
forAll(bm, patchi)
forAll(patches, patchi)
{
if (groupPatchIDs.erase(bm[patchi].name()))
if (groupPatchIDs.erase(patches[patchi].name()))
{
WarningInFunction
<< "Removing patchGroup '" << bm[patchi].name()
<< "Removed patchGroup '" << patches[patchi].name()
<< "' which clashes with patch " << patchi
<< " of the same name."
<< endl;
......@@ -513,46 +592,24 @@ Foam::label Foam::polyBoundaryMesh::nNonProcessor() const
Foam::wordList Foam::polyBoundaryMesh::names() const
{
const polyPatchList& patches = *this;
wordList list(patches.size());
forAll(patches, patchi)
{
list[patchi] = patches[patchi].name();
}
return list;
return getMethodImpl<wordList>(*this, getNameOp<polyPatch>());
}
Foam::wordList Foam::polyBoundaryMesh::types() const
{
const polyPatchList& patches = *this;
wordList list(patches.size());
forAll(patches, patchi)
{
list[patchi] = patches[patchi].type();
}
return list;
return getMethodImpl<wordList>(*this, getTypeOp<polyPatch>());
}
Foam::wordList Foam::polyBoundaryMesh::physicalTypes() const
{
const polyPatchList& patches = *this;
wordList list(patches.size());
forAll(patches, patchi)
{
list[patchi] = patches[patchi].physicalType();
}
return list;
return
getMethodImpl<wordList>
(
*this,
[](const polyPatch& p) { return p.physicalType(); }
);
}
......@@ -578,84 +635,79 @@ Foam::labelRange Foam::polyBoundaryMesh::range(const label patchi) const
}
Foam::labelList Foam::polyBoundaryMesh::findIndices
Foam::labelList Foam::polyBoundaryMesh::indices
(
const keyType& key,
const bool usePatchGroups
const bool useGroups
) const
{
DynamicList<label> indices;
if (key.empty())
{
// no-op
return labelList();
}
else if (key.isPattern())
DynamicList<label> patchIndices;
if (key.isPattern())
{
const regExp keyRe(key);
const regExp matcher(key);
indices = findStrings(keyRe, this->names());
patchIndices = indicesImpl(*this, matcher);
if (usePatchGroups && groupPatchIDs().size())
// Only examine patch groups if requested and when they exist.
if (useGroups && !groupPatchIDs().empty())
{
labelHashSet indexSet(indices);
const wordList allGroupNames = groupPatchIDs().toc();
labelList groupIDs = findStrings(keyRe, allGroupNames);
const wordList groupNames
(
groupPatchIDs().tocKeys(matcher)
);
for (const label groupi : groupIDs)
if (groupNames.size())
{
const word& grpName = allGroupNames[groupi];
labelHashSet groupIndices;
const labelList& patchIDs = groupPatchIDs()[grpName];
for (const label patchi : patchIDs)
for (const word& grpName : groupNames)
{
if (indexSet.insert(patchi))
{
indices.append(patchi);
}
// Hash the patch ids for the group
groupIndices.insert( groupPatchIDs()[grpName] );
}
groupIndices.erase(patchIndices); // Skip existing
patchIndices.append(groupIndices.sortedToc());
}
}
}
else
{
// Literal string. Special version of above to avoid
// unnecessary memory allocations
// Literal string.
// Special version of above for reduced memory footprint
const word& matcher = key;
indices.setCapacity(1);
forAll(*this, i)
const label patchId = findIndexImpl(*this, matcher);
if (patchId >= 0)
{
if (key == operator[](i).name())
{
indices.append(i);
break;
}
patchIndices.append(patchId);
}
if (usePatchGroups && groupPatchIDs().size())
// Only examine patch groups if requested and when they exist.
if (useGroups && !groupPatchIDs().empty())
{
const auto iter = groupPatchIDs().cfind(key);
if (iter.found())
{
labelHashSet indexSet(indices);
const labelList& patchIDs = *iter;
// Hash the patch ids for the group
labelHashSet groupIndices(iter.object());
for (const label patchi : patchIDs)
{
if (indexSet.insert(patchi))
{
indices.append(patchi);
}
}
groupIndices.erase(patchIndices); // Skip existing
patchIndices.append(groupIndices.sortedToc());
}
}
}
return indices;
return patchIndices;
}
......@@ -663,31 +715,20 @@ Foam::label Foam::polyBoundaryMesh::findIndex(const keyType& key) const
{
if (key.empty())
{
// no-op
return -1;
}
else if (key.isPattern())
{
labelList indices = this->findIndices(key);
// Return the first element
if (!indices.empty())
{
return indices.first();
}
// Find as regex
regExp matcher(key);
return findIndexImpl(*this, matcher);
}
else
{
forAll(*this, i)
{
if (key == operator[](i).name())
{
return i;
}
}
// Find as literal string
const word& matcher = key;
return findIndexImpl(*this, matcher);
}
// Not found, return -1
return -1;
}