keyType: Added proper type handling and formalised construction from the string types

Rationalised IO of keyType so the internal structure is not duplicated in
if-else structures in dictionary::entry.
This commit is contained in:
Henry Weller
2019-08-17 10:57:22 +01:00
parent c8f4487a07
commit 0b6346c721
11 changed files with 147 additions and 143 deletions

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | Website: https://openfoam.org \\ / O peration | Website: https://openfoam.org
\\ / A nd | Copyright (C) 2011-2018 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2019 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -52,7 +52,7 @@ int main(int argc, char *argv[])
dictionary fieldNameDict; dictionary fieldNameDict;
forAll(fieldNames, i) forAll(fieldNames, i)
{ {
fieldNameDict.add(fieldNames[i], word(fieldNames[i])); fieldNameDict.add(word(fieldNames[i]), word(fieldNames[i]));
} }
dictionary nameMap; dictionary nameMap;

View File

@ -51,27 +51,9 @@ bool Foam::entry::getKeyword(keyType& keyword, token& keywordToken, Istream& is)
} }
while (keywordToken == token::END_STATEMENT); while (keywordToken == token::END_STATEMENT);
// If the token is a valid keyword set 'keyword' return true... keyword = keywordToken;
if (keywordToken.isWord())
{ return !keyword.isUndefined();
keyword = keywordToken.wordToken();
return true;
}
else if (keywordToken.isVariable())
{
keyword = keywordToken.variableToken();
return true;
}
else if (keywordToken.isString())
{
// Enable wildcards
keyword = keywordToken.stringToken();
return true;
}
else
{
return false;
}
} }
@ -180,7 +162,7 @@ bool Foam::entry::New(dictionary& parentDict, Istream& is)
else if else if
( (
!disableFunctionEntries !disableFunctionEntries
&& keyword[0] == '$' && keyword.isVariable()
) // ... Substitution entry ) // ... Substitution entry
{ {
token nextToken(is); token nextToken(is);

View File

@ -64,17 +64,6 @@ Foam::string Foam::functionEntries::negEntry::negateVariable
// Read variable name as a word including the '$' // Read variable name as a word including the '$'
const variable var(is); const variable var(is);
if (var[0] != '$')
{
FatalIOErrorInFunction
(
parentDict
) << "Expected variable name beginning with a '$' but found '"
<< var << "'" << exit(FatalIOError);
return string::null;
}
// Strip the leading '$' from the variable name // Strip the leading '$' from the variable name
const string varName = var(1, var.size() - 1); const string varName = var(1, var.size() - 1);

View File

@ -41,28 +41,28 @@ void Foam::primitiveEntry::append(const UList<token>& varTokens)
bool Foam::primitiveEntry::expandVariable bool Foam::primitiveEntry::expandVariable
( (
const string& w, const variable& w,
const dictionary& dict const dictionary& dict
) )
{ {
if (w.size() > 2 && w[0] == '$' && w[1] == token::BEGIN_BLOCK) if (w.size() > 2 && w[0] == '$' && w[1] == token::BEGIN_BLOCK)
{ {
// Recursive substitution mode. Replace between {} with expansion. // Recursive substitution mode. Replace between {} with expansion.
string s(w(2, w.size()-3)); string s(w(2, w.size() - 3));
// Substitute dictionary and environment variables. Do not allow // Substitute dictionary and environment variables. Do not allow
// empty substitutions. // empty substitutions.
stringOps::inplaceExpand(s, dict, true, false); stringOps::inplaceExpand(s, dict, true, false);
string newW(w); variable newW(w);
newW.std::string::replace(1, newW.size()-1, s); newW.std::string::replace(1, newW.size() - 1, s);
return expandVariable(newW, dict); return expandVariable(newW, dict);
} }
else else
{ {
string varName = w(1, w.size()-1); string varName = w(1, w.size() - 1);
// lookup the variable name in the given dictionary.... // Lookup the variable name in the given dictionary....
// Note: allow wildcards to match? For now disabled since following // Note: allow wildcards to match? For now disabled since following
// would expand internalField to wildcard match and not expected // would expand internalField to wildcard match and not expected
// internalField: // internalField:
@ -84,7 +84,7 @@ bool Foam::primitiveEntry::expandVariable
} }
else else
{ {
// not in the dictionary - try an environment variable // Not in the dictionary - try an environment variable
string envStr = getEnv(varName); string envStr = getEnv(varName);
if (envStr.empty()) if (envStr.empty())

View File

@ -71,23 +71,13 @@ class primitiveEntry
void append(const UList<token>&); void append(const UList<token>&);
//- Append the given token to this entry //- Append the given token to this entry
void append void append(const token& currToken, const dictionary&, Istream&);
(
const token& currToken,
const dictionary&,
Istream&
);
//- Expand the given variable (keyword starts with $) //- Expand the given variable
bool expandVariable(const string&, const dictionary&); bool expandVariable(const variable&, const dictionary&);
//- Expand the given function (keyword starts with #) //- Expand the given function (keyword starts with #)
bool expandFunction bool expandFunction(const word&, const dictionary&, Istream&);
(
const word&,
const dictionary&,
Istream&
);
//- Read the complete entry from the given stream //- Read the complete entry from the given stream
void readEntry(const dictionary&, Istream&); void readEntry(const dictionary&, Istream&);

View File

@ -60,7 +60,7 @@ void Foam::primitiveEntry::append
( (
disableFunctionEntries disableFunctionEntries
|| v.size() == 1 || v.size() == 1
|| !(v[0] == '$' && expandVariable(v, dict)) || !expandVariable(v, dict)
) )
{ {
newElmt(tokenIndex()++) = currToken; newElmt(tokenIndex()++) = currToken;

View File

@ -178,7 +178,7 @@ Foam::labelList Foam::processorCyclicPolyPatch::patchIDs
{ {
return bm.findIndices return bm.findIndices
( (
string("procBoundary.*to.*through" + cyclicPolyPatchName) keyType(string("procBoundary.*to.*through" + cyclicPolyPatchName))
); );
} }

View File

@ -21,9 +21,6 @@ License
You should have received a copy of the GNU General Public License You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Description
Istream constructor and IOstream operators for keyType.
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "keyType.H" #include "keyType.H"
@ -37,10 +34,19 @@ const Foam::keyType Foam::keyType::null;
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::keyType::keyType(const token& t)
:
variable(),
type_(UNDEFINED)
{
operator=(t);
}
Foam::keyType::keyType(Istream& is) Foam::keyType::keyType(Istream& is)
: :
variable(), variable(),
isPattern_(false) type_(UNDEFINED)
{ {
is >> *this; is >> *this;
} }
@ -54,19 +60,52 @@ bool Foam::keyType::match
bool literalMatch bool literalMatch
) const ) const
{ {
if (literalMatch || !isPattern_) if (literalMatch || !isPattern())
{ {
// check as string // Check as string
return (str == *this); return (str == *this);
} }
else else
{ {
// check as regex // Check as regex
return regExp(*this).match(str); return regExp(*this).match(str);
} }
} }
// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
void Foam::keyType::operator=(const token& t)
{
if (t.isWord())
{
operator=(t.wordToken());
}
else if (t.isVariable())
{
operator=(t.variableToken());
}
else if (t.isString())
{
// Assign from string. Set as pattern.
operator=(t.stringToken());
// An empty pattern string is a fatal error
if (empty())
{
FatalErrorInFunction
<< "Empty pattern string"
<< exit(FatalIOError);
}
}
else
{
variable::clear();
type_ = UNDEFINED;
}
}
// * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * // // * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * //
Foam::Istream& Foam::operator>>(Istream& is, keyType& kw) Foam::Istream& Foam::operator>>(Istream& is, keyType& kw)
@ -79,27 +118,9 @@ Foam::Istream& Foam::operator>>(Istream& is, keyType& kw)
return is; return is;
} }
if (t.isWord()) kw = t;
{
kw = t.wordToken();
}
else if (t.isString())
{
// Assign from string. Set as regular expression.
kw = t.stringToken();
kw.isPattern_ = true;
// flag empty strings as an error if (kw.isUndefined())
if (kw.empty())
{
is.setBad();
FatalIOErrorInFunction(is)
<< "empty word/expression "
<< exit(FatalIOError);
return is;
}
}
else
{ {
is.setBad(); is.setBad();
FatalIOErrorInFunction(is) FatalIOErrorInFunction(is)

View File

@ -48,6 +48,7 @@ namespace Foam
// Forward declaration of classes // Forward declaration of classes
class Istream; class Istream;
class Ostream; class Ostream;
class token;
// Forward declaration of friend functions and operators // Forward declaration of friend functions and operators
@ -66,16 +67,20 @@ class keyType
: :
public variable public variable
{ {
//- Enumeration of the keyword types
enum type
{
UNDEFINED,
WORD,
VARIABLE,
PATTERN
};
// Private Data // Private Data
//- Is the keyType a pattern (regular expression) //- The type of this keyword
bool isPattern_; type type_;
// Private Member Functions
//- Disallow assignments where we cannot determine string/word type
void operator=(const std::string&);
public: public:
@ -94,29 +99,33 @@ public:
//- Copy constructor //- Copy constructor
inline keyType(const keyType&); inline keyType(const keyType&);
//- Copy constructor of variable. Not treated as a regular expression //- Construct as word
inline keyType(const variable&);
//- Copy constructor of word. Not treated as a regular expression
inline keyType(const word&); inline keyType(const word&);
//- Copy constructor of string. Treat as regular expression. //- Construct as variable
inline keyType(const string&); inline explicit keyType(const variable&);
//- Copy constructor of character array. //- Construct as pattern
// Not treated as a regular expression inline explicit keyType(const string&);
//- Construct as word from character array.
inline keyType(const char*); inline keyType(const char*);
//- Copy constructor of std::string with specified treatment //- Construct from token
inline keyType(const std::string&, const bool isPattern); explicit keyType(const token&);
//- Construct from Istream //- Construct from Istream
// Treat as regular expression if surrounded by quotation marks. explicit keyType(Istream&);
keyType(Istream&);
// Member Functions // Member Functions
//- Return true if the type has not been defined
inline bool isUndefined() const;
//- Return true if the keyword is a variable
inline bool isVariable() const;
//- Should be treated as a match rather than a literal string //- Should be treated as a match rather than a literal string
inline bool isPattern() const; inline bool isPattern() const;
@ -132,18 +141,24 @@ public:
//- Assignment operator //- Assignment operator
inline void operator=(const keyType&); inline void operator=(const keyType&);
//- Assign as variable, not as non regular expression //- Assign as variable
inline void operator=(const variable&); inline void operator=(const variable&);
//- Assign as word, not as non regular expression //- Assign as word
inline void operator=(const word&); inline void operator=(const word&);
//- Assign as regular expression //- Assign as pattern
inline void operator=(const string&); inline void operator=(const string&);
//- Assign as word, not as non regular expression //- Assign as word
inline void operator=(const char*); inline void operator=(const char*);
//- Disallow assignments where we cannot determine string/word type
void operator=(const std::string&) = delete;
//- Assign from token setting the appropriate type
void operator=(const token&);
// IOstream Operators // IOstream Operators

View File

@ -28,57 +28,62 @@ License
inline Foam::keyType::keyType() inline Foam::keyType::keyType()
: :
variable(), variable(),
isPattern_(false) type_(UNDEFINED)
{} {}
inline Foam::keyType::keyType(const keyType& k) inline Foam::keyType::keyType(const keyType& k)
: :
variable(k), variable(k),
isPattern_(k.isPattern()) type_(k.type_)
{} {}
inline Foam::keyType::keyType(const word& w) inline Foam::keyType::keyType(const word& w)
: :
variable(w), variable(w),
isPattern_(false) type_(WORD)
{} {}
inline Foam::keyType::keyType(const variable& v) inline Foam::keyType::keyType(const variable& v)
: :
variable(v), variable(v),
isPattern_(false) type_(VARIABLE)
{} {}
inline Foam::keyType::keyType(const string& s) inline Foam::keyType::keyType(const string& s)
: :
variable(s, false), variable(s, false),
isPattern_(true) type_(PATTERN)
{} {}
inline Foam::keyType::keyType(const char* s) inline Foam::keyType::keyType(const char* s)
: :
variable(s, false), variable(s, true),
isPattern_(false) type_(WORD)
{}
inline Foam::keyType::keyType(const std::string& s, const bool isPattern)
:
variable(s, false),
isPattern_(isPattern)
{} {}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
inline bool Foam::keyType::isUndefined() const
{
return type_ == UNDEFINED;
}
inline bool Foam::keyType::isVariable() const
{
return type_ == VARIABLE;
}
inline bool Foam::keyType::isPattern() const inline bool Foam::keyType::isPattern() const
{ {
return isPattern_; return type_ == PATTERN;
} }
@ -87,37 +92,35 @@ inline bool Foam::keyType::isPattern() const
inline void Foam::keyType::operator=(const keyType& k) inline void Foam::keyType::operator=(const keyType& k)
{ {
variable::operator=(k); variable::operator=(k);
isPattern_ = k.isPattern_; type_ = k.type_;
}
inline void Foam::keyType::operator=(const variable& v)
{
variable::operator=(v);
isPattern_ = false;
} }
inline void Foam::keyType::operator=(const word& w) inline void Foam::keyType::operator=(const word& w)
{ {
variable::operator=(w); variable::operator=(w);
isPattern_ = false; type_ = WORD;
}
inline void Foam::keyType::operator=(const variable& v)
{
variable::operator=(v);
type_ = VARIABLE;
} }
inline void Foam::keyType::operator=(const string& s) inline void Foam::keyType::operator=(const string& s)
{ {
// Bypass checking
string::operator=(s); string::operator=(s);
isPattern_ = true; type_ = PATTERN;
} }
inline void Foam::keyType::operator=(const char* s) inline void Foam::keyType::operator=(const char* s)
{ {
// Bypass checking word::operator=(s);
string::operator=(s); type_ = WORD;
isPattern_ = false;
} }

View File

@ -86,20 +86,24 @@ public:
inline variable(const variable&); inline variable(const variable&);
//- Copy constructor of word //- Copy constructor of word
inline variable(const word&); inline explicit variable(const word&);
//- Copy constructor of string //- Copy constructor of string
inline variable(const string&, const bool doStripInvalid=true); inline explicit variable(const string&, const bool doStripInvalid=true);
//- Copy constructor of std::string //- Copy constructor of std::string
inline variable(const std::string&, const bool doStripInvalid=true); inline explicit variable
(
const std::string&,
const bool doStripInvalid=true
);
//- Copy constructor of character array //- Copy constructor of character array
inline variable(const char*, const bool doStripInvalid=true); inline explicit variable(const char*, const bool doStripInvalid=true);
//- Construct from Istream //- Construct from Istream
// Words are treated as literals, strings with an auto-test // Words are treated as literals, strings with an auto-test
variable(Istream&); explicit variable(Istream&);
// Member Functions // Member Functions