mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
ENH: additional fileName methods
- add an extension to the file name
- remove a file extension
- check if a file name has an extension
- check if a file name has a particular extension (as word),
or matches a particular grouping of extensions (as wordRe).
This commit is contained in:
@ -37,6 +37,7 @@ Description
|
|||||||
#include "IOstreams.H"
|
#include "IOstreams.H"
|
||||||
#include "OSspecific.H"
|
#include "OSspecific.H"
|
||||||
#include "POSIX.H"
|
#include "POSIX.H"
|
||||||
|
#include "Switch.H"
|
||||||
#include "etcFiles.H"
|
#include "etcFiles.H"
|
||||||
|
|
||||||
using namespace Foam;
|
using namespace Foam;
|
||||||
@ -47,6 +48,7 @@ using namespace Foam;
|
|||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
argList::noParallel();
|
argList::noParallel();
|
||||||
|
argList::addBoolOption("ext", "test handing of file extensions");
|
||||||
argList::addBoolOption("construct", "test constructors");
|
argList::addBoolOption("construct", "test constructors");
|
||||||
argList::addBoolOption("default", "reinstate default tests");
|
argList::addBoolOption("default", "reinstate default tests");
|
||||||
argList::addNote("runs default tests or specified ones only");
|
argList::addNote("runs default tests or specified ones only");
|
||||||
@ -108,6 +110,131 @@ int main(int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Test various ext() methods
|
||||||
|
if (args.optionFound("ext"))
|
||||||
|
{
|
||||||
|
Info<<nl << nl << "handling of fileName extension" << nl;
|
||||||
|
|
||||||
|
fileName empty;
|
||||||
|
fileName endWithDot("some.path/name.");
|
||||||
|
fileName endWithSlash("some.path/");
|
||||||
|
fileName input0("some.file/with.out/extension");
|
||||||
|
fileName input1("path.to/media/image.png");
|
||||||
|
|
||||||
|
Info<<"File : " << input0 << " ext: "
|
||||||
|
<< Switch(input0.hasExt())
|
||||||
|
<< " = " << input0.ext() << nl;
|
||||||
|
Info<<"File : " << input1 << " ext: "
|
||||||
|
<< Switch(input1.hasExt())
|
||||||
|
<< " = " << input1.ext() << nl;
|
||||||
|
Info<<"File : " << endWithDot << " ext: "
|
||||||
|
<< Switch(endWithDot.hasExt())
|
||||||
|
<< " = " << endWithDot.ext() << " <-- perhaps return false?" << nl;
|
||||||
|
Info<<"File : " << endWithSlash << " ext: "
|
||||||
|
<< Switch(endWithSlash.hasExt())
|
||||||
|
<< " = " << endWithSlash.ext() << nl;
|
||||||
|
|
||||||
|
|
||||||
|
Info<<"Remove extension " << (input0.removeExt());
|
||||||
|
Info<< " now: " << input0 << nl;
|
||||||
|
|
||||||
|
Info<<"Remove extension " << (input1.removeExt());
|
||||||
|
Info<< " now: " << input1 << nl;
|
||||||
|
|
||||||
|
Info<<"Remove extension " << (endWithSlash.removeExt());
|
||||||
|
Info<< " now: " << endWithSlash << nl;
|
||||||
|
|
||||||
|
wordList exts{ "jpg", "png", "txt", word::null };
|
||||||
|
Info<<"Add extension(s): " << input1 << nl;
|
||||||
|
for (const word& e : exts)
|
||||||
|
{
|
||||||
|
Info<<"<" << e << "> -> " << input1.ext(e) << nl;
|
||||||
|
}
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
|
||||||
|
Info<<"Test hasExt(word)" << nl
|
||||||
|
<<"~~~~~~~~~~~~~~~~~" << nl;
|
||||||
|
Info<<"Has extension(s):" << nl
|
||||||
|
<< "input: " << input1 << nl;
|
||||||
|
for (const word& e : exts)
|
||||||
|
{
|
||||||
|
Info<<" '" << e << "' -> "
|
||||||
|
<< Switch(input1.hasExt(e)) << nl;
|
||||||
|
}
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
Info<<"Has extension(s):" << nl
|
||||||
|
<< "input: " << endWithDot << nl;
|
||||||
|
for (const word& e : exts)
|
||||||
|
{
|
||||||
|
Info<<" '" << e << "' -> "
|
||||||
|
<< Switch(endWithDot.hasExt(e)) << nl;
|
||||||
|
}
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
|
||||||
|
Info<<"Test hasExt(wordRe)" << nl
|
||||||
|
<<"~~~~~~~~~~~~~~~~~~~" << nl;
|
||||||
|
|
||||||
|
// A regex with a zero length matcher doesn't work at all:
|
||||||
|
// eg "(png|jpg|txt|)" regex matcher itself
|
||||||
|
|
||||||
|
wordRe matcher0("()", wordRe::REGEXP);
|
||||||
|
wordRe matcher1("(png|jpg|txt)", wordRe::REGEXP);
|
||||||
|
wordRe matcher2("(png|txt)", wordRe::REGEXP);
|
||||||
|
|
||||||
|
Info<<"Has extension(s):" << nl
|
||||||
|
<< "input: " << endWithDot << nl;
|
||||||
|
Info<<" " << matcher0 << " -> "
|
||||||
|
<< Switch(endWithDot.hasExt(matcher0)) << nl;
|
||||||
|
Info<<" " << matcher1 << " -> "
|
||||||
|
<< Switch(endWithDot.hasExt(matcher1)) << nl;
|
||||||
|
Info<<" " << matcher2 << " -> "
|
||||||
|
<< Switch(endWithDot.hasExt(matcher2)) << nl;
|
||||||
|
|
||||||
|
Info<< "input: " << input1 << nl;
|
||||||
|
Info<<" " << matcher0 << " -> "
|
||||||
|
<< Switch(input1.hasExt(matcher0)) << nl;
|
||||||
|
Info<<" " << matcher1 << " -> "
|
||||||
|
<< Switch(input1.hasExt(matcher1)) << nl;
|
||||||
|
Info<<" " << matcher2 << " -> "
|
||||||
|
<< Switch(input1.hasExt(matcher2)) << nl;
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
Info<<"Remove extension(s):" << nl << "input: " << input1 << nl;
|
||||||
|
while (!input1.empty())
|
||||||
|
{
|
||||||
|
if (input1.removeExt())
|
||||||
|
{
|
||||||
|
Info<< " -> " << input1 << nl;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Info<< "stop> " << input1 << nl;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
input0.clear();
|
||||||
|
Info<<"test with zero-sized: " << input0 << nl;
|
||||||
|
Info<<"add extension: " << input0.ext("abc") << nl;
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
input0 = "this/";
|
||||||
|
Info<<"test add after slash: " << input0 << nl;
|
||||||
|
Info<<"add extension: " << input0.ext("abc")
|
||||||
|
<< " <-- avoids accidentally creating hidden files" << nl;
|
||||||
|
Info<< nl;
|
||||||
|
|
||||||
|
input0 = "this.file.";
|
||||||
|
Info<<"test after dot: " << input0 << nl;
|
||||||
|
Info<<"add extension: " << input0.ext("abc")
|
||||||
|
<< " <-- No check for repeated dots (user error!)" << nl;
|
||||||
|
Info<< nl;
|
||||||
|
}
|
||||||
|
|
||||||
if (!defaultTests)
|
if (!defaultTests)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
@ -27,6 +27,7 @@ License
|
|||||||
#include "wordList.H"
|
#include "wordList.H"
|
||||||
#include "DynamicList.H"
|
#include "DynamicList.H"
|
||||||
#include "OSspecific.H"
|
#include "OSspecific.H"
|
||||||
|
#include "wordRe.H"
|
||||||
|
|
||||||
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
|
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
|
||||||
|
|
||||||
@ -303,9 +304,9 @@ Foam::fileName Foam::fileName::path() const
|
|||||||
|
|
||||||
Foam::fileName Foam::fileName::lessExt() const
|
Foam::fileName Foam::fileName::lessExt() const
|
||||||
{
|
{
|
||||||
size_type i = find_last_of("./");
|
size_type i = find_ext();
|
||||||
|
|
||||||
if (i == npos || i == 0 || operator[](i) == '/')
|
if (i == npos)
|
||||||
{
|
{
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@ -318,9 +319,9 @@ Foam::fileName Foam::fileName::lessExt() const
|
|||||||
|
|
||||||
Foam::word Foam::fileName::ext() const
|
Foam::word Foam::fileName::ext() const
|
||||||
{
|
{
|
||||||
size_type i = find_last_of("./");
|
size_type i = find_ext();
|
||||||
|
|
||||||
if (i == npos || i == 0 || operator[](i) == '/')
|
if (i == npos)
|
||||||
{
|
{
|
||||||
return word::null;
|
return word::null;
|
||||||
}
|
}
|
||||||
@ -331,6 +332,71 @@ Foam::word Foam::fileName::ext() const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Foam::fileName& Foam::fileName::ext(const word& ending)
|
||||||
|
{
|
||||||
|
if (!ending.empty() && !empty() && operator[](size()-1) != '/')
|
||||||
|
{
|
||||||
|
append(".");
|
||||||
|
append(ending);
|
||||||
|
}
|
||||||
|
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool Foam::fileName::hasExt() const
|
||||||
|
{
|
||||||
|
return (find_ext() != npos);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool Foam::fileName::hasExt(const word& ending) const
|
||||||
|
{
|
||||||
|
size_type i = find_ext();
|
||||||
|
if (i == npos)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
++i; // Do next comparison *after* the dot
|
||||||
|
return
|
||||||
|
(
|
||||||
|
// Lengths must match
|
||||||
|
((size() - i) == ending.size())
|
||||||
|
&& !compare(i, npos, ending)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool Foam::fileName::hasExt(const wordRe& ending) const
|
||||||
|
{
|
||||||
|
size_type i = find_ext();
|
||||||
|
if (i == npos)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string end = substr(i+1, npos);
|
||||||
|
return ending.match(end);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool Foam::fileName::removeExt()
|
||||||
|
{
|
||||||
|
const size_type i = find_ext();
|
||||||
|
|
||||||
|
if (i == npos)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this->resize(i);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
Foam::wordList Foam::fileName::components(const char delimiter) const
|
Foam::wordList Foam::fileName::components(const char delimiter) const
|
||||||
{
|
{
|
||||||
DynamicList<word> wrdList(20);
|
DynamicList<word> wrdList(20);
|
||||||
|
|||||||
@ -57,6 +57,7 @@ template<class T> class UList;
|
|||||||
typedef List<word> wordList;
|
typedef List<word> wordList;
|
||||||
|
|
||||||
// Forward declaration of friend functions and operators
|
// Forward declaration of friend functions and operators
|
||||||
|
class wordRe;
|
||||||
class fileName;
|
class fileName;
|
||||||
|
|
||||||
Istream& operator>>(Istream&, fileName&);
|
Istream& operator>>(Istream&, fileName&);
|
||||||
@ -73,6 +74,10 @@ class fileName
|
|||||||
{
|
{
|
||||||
// Private Member Functions
|
// Private Member Functions
|
||||||
|
|
||||||
|
//- Find position of the file extension dot, return npos on failure.
|
||||||
|
// A wrapped version of find_last_of("./") with additional logic.
|
||||||
|
inline size_type find_ext() const;
|
||||||
|
|
||||||
//- Strip invalid characters
|
//- Strip invalid characters
|
||||||
inline void stripInvalid();
|
inline void stripInvalid();
|
||||||
|
|
||||||
@ -104,35 +109,35 @@ public:
|
|||||||
inline fileName();
|
inline fileName();
|
||||||
|
|
||||||
//- Construct as copy
|
//- Construct as copy
|
||||||
inline fileName(const fileName&);
|
inline fileName(const fileName& fn);
|
||||||
|
|
||||||
//- Construct as copy of word
|
//- Construct as copy of word
|
||||||
inline fileName(const word&);
|
inline fileName(const word& s);
|
||||||
|
|
||||||
//- Construct as copy of string
|
//- Construct as copy of string
|
||||||
inline fileName(const string&, const bool doStripInvalid=true);
|
inline fileName(const string& s, const bool doStripInvalid=true);
|
||||||
|
|
||||||
//- Construct as copy of std::string
|
//- Construct as copy of std::string
|
||||||
inline fileName(const std::string&, const bool doStripInvalid=true);
|
inline fileName(const std::string& s, const bool doStripInvalid=true);
|
||||||
|
|
||||||
//- Construct as copy of character array
|
//- Construct as copy of character array
|
||||||
inline fileName(const char*, const bool doStripInvalid=true);
|
inline fileName(const char* s, const bool doStripInvalid=true);
|
||||||
|
|
||||||
//- Construct by concatenating elements of wordList separated by '/'
|
//- Construct by concatenating elements of wordList separated by '/'
|
||||||
explicit fileName(const UList<word>&);
|
explicit fileName(const UList<word>& lst);
|
||||||
|
|
||||||
//- Construct by concatenating words separated by '/'
|
//- Construct by concatenating words separated by '/'
|
||||||
explicit fileName(std::initializer_list<word>);
|
explicit fileName(std::initializer_list<word> lst);
|
||||||
|
|
||||||
|
|
||||||
//- Construct from Istream
|
//- Construct from Istream
|
||||||
fileName(Istream&);
|
fileName(Istream& is);
|
||||||
|
|
||||||
|
|
||||||
// Member functions
|
// Member functions
|
||||||
|
|
||||||
//- Is this character valid for a fileName?
|
//- Is this character valid for a fileName?
|
||||||
inline static bool valid(char);
|
inline static bool valid(char c);
|
||||||
|
|
||||||
//- Cleanup file name
|
//- Cleanup file name
|
||||||
//
|
//
|
||||||
@ -209,6 +214,24 @@ public:
|
|||||||
//- Return file name extension (part after last .)
|
//- Return file name extension (part after last .)
|
||||||
word ext() const;
|
word ext() const;
|
||||||
|
|
||||||
|
//- Append a '.' and the ending, and return the object.
|
||||||
|
// The '.' and ending will not be added when the ending is empty,
|
||||||
|
// or when the file name is empty or ended with a '/'.
|
||||||
|
fileName& ext(const word& ending);
|
||||||
|
|
||||||
|
//- Return true if it has an extension or simply ends with a '.'
|
||||||
|
bool hasExt() const;
|
||||||
|
|
||||||
|
//- Return true if the extension is the same as the given ending.
|
||||||
|
bool hasExt(const word& ending) const;
|
||||||
|
|
||||||
|
//- Return true if the extension matches the given ending.
|
||||||
|
bool hasExt(const wordRe& ending) const;
|
||||||
|
|
||||||
|
//- Remove extension, returning true if string changed.
|
||||||
|
bool removeExt();
|
||||||
|
|
||||||
|
|
||||||
//- Return path components as wordList
|
//- Return path components as wordList
|
||||||
//
|
//
|
||||||
// Behaviour:
|
// Behaviour:
|
||||||
@ -219,32 +242,46 @@ public:
|
|||||||
// "foo/bar" 2("foo", "bar")
|
// "foo/bar" 2("foo", "bar")
|
||||||
// "/foo/bar" 2("foo", "bar")
|
// "/foo/bar" 2("foo", "bar")
|
||||||
// "/foo/bar/" 2("foo", "bar")
|
// "/foo/bar/" 2("foo", "bar")
|
||||||
wordList components(const char delimiter='/') const;
|
wordList components(const char delimiter = '/') const;
|
||||||
|
|
||||||
//- Return a single component of the path
|
//- Return a single component of the path
|
||||||
word component(const size_type, const char delimiter='/') const;
|
word component
|
||||||
|
(
|
||||||
|
const size_type cmpt,
|
||||||
|
const char delimiter = '/'
|
||||||
|
) const;
|
||||||
|
|
||||||
|
|
||||||
// Member operators
|
// Member operators
|
||||||
|
|
||||||
// Assignment
|
// Assignment
|
||||||
|
|
||||||
void operator=(const fileName&);
|
//- Copy, no character validation required
|
||||||
void operator=(const word&);
|
void operator=(const fileName& str);
|
||||||
void operator=(const string&);
|
|
||||||
void operator=(const std::string&);
|
//- Copy, no character validation required
|
||||||
void operator=(const char*);
|
void operator=(const word& str);
|
||||||
|
|
||||||
|
//- Copy, stripping invalid characters
|
||||||
|
void operator=(const string& str);
|
||||||
|
|
||||||
|
//- Copy, stripping invalid characters
|
||||||
|
void operator=(const std::string& str);
|
||||||
|
|
||||||
|
//- Copy, stripping invalid characters
|
||||||
|
void operator=(const char* str);
|
||||||
|
|
||||||
|
|
||||||
// IOstream operators
|
// IOstream operators
|
||||||
|
|
||||||
friend Istream& operator>>(Istream&, fileName&);
|
friend Istream& operator>>(Istream& is, fileName& fn);
|
||||||
friend Ostream& operator<<(Ostream&, const fileName&);
|
friend Ostream& operator<<(Ostream& os, const fileName& fn);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
//- Assemble words and fileNames as pathnames by adding a '/' separator
|
//- Assemble words and fileNames as pathnames by adding a '/' separator.
|
||||||
fileName operator/(const string&, const string&);
|
// No '/' separator is added if either argument is an empty string.
|
||||||
|
fileName operator/(const string& a, const string& b);
|
||||||
|
|
||||||
|
|
||||||
//- Recursively search the given directory for the file
|
//- Recursively search the given directory for the file
|
||||||
|
|||||||
@ -25,6 +25,21 @@ License
|
|||||||
|
|
||||||
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
||||||
|
|
||||||
|
inline std::string::size_type Foam::fileName::find_ext() const
|
||||||
|
{
|
||||||
|
const size_type i = find_last_of("./");
|
||||||
|
|
||||||
|
if (i == npos || i == 0 || operator[](i) == '/')
|
||||||
|
{
|
||||||
|
return npos;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
inline void Foam::fileName::stripInvalid()
|
inline void Foam::fileName::stripInvalid()
|
||||||
{
|
{
|
||||||
// skip stripping unless debug is active to avoid
|
// skip stripping unless debug is active to avoid
|
||||||
|
|||||||
@ -78,5 +78,3 @@ Foam::Ostream& Foam::operator<<(Ostream& os, const fileName& fn)
|
|||||||
|
|
||||||
|
|
||||||
// ************************************************************************* //
|
// ************************************************************************* //
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user