- prefer csorted() method for const access since it ensures that the
return values are also const pointers (for example) even if
the object itself can be accessed as a non-const.
- the csorted() method already existed for HashTable and
objectRegistry, but now added to IOobjectList for method name
consistency (even although the IOobjectList only has a const-access
version)
ENH: objectRegistry with templated strict lookup
- for lookupClass and csorted/sorted. Allows isType restriction as a
compile-time specification.
- name and functionality similar to std::unordered_map (C++17).
Formalizes what had been previously been implemented in IOobjectList
but now manages without pointer deletion/creation.
- returns UPtrList view (read-only or read/write) of the objects
- shorter names for IOobject checks: hasHeaderClass(), isHeaderClass()
- remove unused IOobject::isHeaderClassName(const word&) method.
The typed versions are preferable/recommended, but can still check
directly if needed:
(io.headerClassName() == "foo")
- cfindObject() for const pointer access.
- getObject() for mutable non-const pointer access, similar to the
objectRegistry::getObjectPtr()
- cfindObject(), findObject(), getObject() with template type access
to also check the headerClassName.
For example,
cfindObject("U") -> good
cfindObject<volVectorField>("U") -> good
cfindObject<volScalarField>("U") -> nullptr
This allows inversion of looping logic.
1) Obtain the names for a particular Type
for (const word& objName : objs.sortedNames<Type>())
{
const IOobject* io = objs[objName];
...
}
2) Use previously obtained names and apply to a particular Type
for (const word& objName : someListOfNames)
{
const IOobject* io = objs.cfindObject<Type>(objName);
if (io)
{
...
}
}
- support name filtering by class based on <Type> or predicates.
Eg,
objects.sortedNames<volScalarField>(namePattern);
vs objects.sortedNames(volScalarField::typeName, namePattern);
These can also be used directly for untyped name matching.
Eg,
objects.sortedNames<void>(namePattern);
Can also use a predicate:
objects.sortedNames(wordRe("vol.*Field"), namePattern);
objects.sortedNames
(
[](const word& clsName){ return clsName.startsWith("vol"); },
namePattern
);
- naming similar to objectRegistry, with unambiguous resolution.
The lookup() methods have different return types depending on the
calling parameter.
STYLE: use IOobjectListTemplates.C for implementations
- previously included as local definition within IOobjectList.C,
but will be adding more templated methods soon.
- adjust parameters (eg, matchName instead of matcher) to show their
function
ENH: handle objectRegistry::names<void>(...)
- this is equivalent to no Type restriction, and can be used when
filtering names. Eg,
obr.names<void>(wordRe..);
- use succincter method names that more closely resemble dictionary
and HashTable method names. This improves method name consistency
between classes and also requires less typing effort:
args.found(optName) vs. args.optionFound(optName)
args.readIfPresent(..) vs. args.optionReadIfPresent(..)
...
args.opt<scalar>(optName) vs. args.optionRead<scalar>(optName)
args.read<scalar>(index) vs. args.argRead<scalar>(index)
- the older method names forms have been retained for code compatibility,
but are now deprecated
- provides a summary hash of classes used and their associated object names.
The HashTable representation allows us to leverage various HashTable
methods. This hashed summary view can be useful when querying
particular aspects, but is most useful when reducing the objects in
consideration to a particular subset. For example,
const wordHashSet interestingTypes
{
volScalarField::typeName,
volVectorField::typeName
};
IOobjectList objects(runTime, runTime.timeName());
HashTable<wordHashSet> classes = objects.classes();
classes.retain(interestingTypes);
// Or do just the opposite:
classes.erase(unsupportedTypes);
Can also use the underlying HashTable filter methods
STYLE: use templated internals to avoid findString() when matching subsets