X-Git-Url: http://git.tdb.fi/?p=libs%2Fcore.git;a=blobdiff_plain;f=source%2Ffs%2Fpath.h;h=82600dc35c28d5787f69b56f0af3b8b12af50f22;hp=6aa16f6d08191a9d7d4000f8f9be65ee4d6217a6;hb=5a32939eb6e576c223e1be5f80226d9e628a2398;hpb=8552e6a4e4fbc454e08c582d1dbcd55ab58a3c37 diff --git a/source/fs/path.h b/source/fs/path.h index 6aa16f6..82600dc 100644 --- a/source/fs/path.h +++ b/source/fs/path.h @@ -3,13 +3,14 @@ #include #include +#include namespace Msp { namespace FS { enum { -#ifdef WIN32 +#ifdef _WIN32 DIRSEP = '\\' #else DIRSEP = '/' @@ -20,29 +21,53 @@ enum Stores a filesystem path. Paths are always stored in a normalized form; there are never any "." or ".." components in the middle of the path, and relative paths always begin with a single "." component or a sequence ".." components. +As a special case, calling the constructor with no arguments or with an empty +string will construct an empty path; this can be usedful as an invalid value. + +A path can also be treated as an array of components, supporting indexing, +iteration and slicing. In this context the root directory is treated as a +component of its own. */ class Path { +private: + typedef std::vector PositionArray; + public: class Iterator { - friend class Path; + public: + typedef PositionArray::difference_type difference_type; + typedef const std::string value_type; + typedef const std::string *pointer; + typedef const std::string &reference; + typedef std::input_iterator_tag iterator_category; private: - const Path &path; - std::string::size_type start,end; + const Path *path; + PositionArray::const_iterator iter; + bool end; + std::string current; - Iterator(const Path &); + Iterator(const Path &, bool = false); public: + static Iterator at_begin(const Path &p) { return Iterator(p); } + static Iterator at_end(const Path &p) { return Iterator(p, true); } + Iterator &operator++(); + Iterator operator++(int) { Iterator i = *this; ++*this; return i; } Iterator &operator--(); - std::string operator*() const; - bool operator==(const Iterator &i) const { return (start==i.start && end==i.end); } + const std::string &operator*() const { return current; } + const std::string *operator->() const { return ¤t; } + bool operator==(const Iterator &i) const { return (iter==i.iter && end==i.end); } bool operator!=(const Iterator &i) const { return !(*this==i); } + private: + void update(); }; private: std::string path; + std::vector separators; public: Path(); @@ -52,20 +77,26 @@ private: void init(const std::string &); public: + /// Returns the path as a string. const std::string &str() const { return path; } + /// Returns the path as a pointer to a null-terminated string. + const char *c_str() const { return path.c_str(); } + /// Returns the number of components in the path. unsigned size() const; + /** Indicates whether the path is empty. This really means empty; a path + pointing to the current directory is not empty. */ bool empty() const { return path.empty(); } - /// Determines whether the path starts from the root directory + /// Determines whether the path starts from the root directory. bool is_absolute() const; /// Extracts a range of components from the path. Path subpath(unsigned start, unsigned count = static_cast(-1)) const; - /// Concatenates this path with another one, with usual filesystem semantics + /// Concatenates this path with another one, with usual filesystem semantics. Path operator/(const Path &p) const; Path &operator/=(const Path &); @@ -80,8 +111,14 @@ public: std::string operator[](int) const; bool operator==(const Path &) const; - Iterator begin() const; - Iterator end() const; + bool operator<(const Path &) const; + bool operator>(const Path &) const; + bool operator<=(const Path &other) const { return !(*this>other); } + bool operator>=(const Path &other) const { return !(*this