diff options
-rw-r--r-- | libbutl/path-io.mxx | 13 | ||||
-rw-r--r-- | libbutl/path.ixx | 24 | ||||
-rw-r--r-- | libbutl/path.mxx | 7 | ||||
-rw-r--r-- | tests/path/driver.cxx | 28 |
4 files changed, 60 insertions, 12 deletions
diff --git a/libbutl/path-io.mxx b/libbutl/path-io.mxx index 5a91dac..a44d26b 100644 --- a/libbutl/path-io.mxx +++ b/libbutl/path-io.mxx @@ -31,16 +31,17 @@ import butl.path; LIBBUTL_MODEXPORT namespace butl { - // This is the default path IO implementation. It is separate to allo custom - // implementations. For example, we may want to print paths as relative to - // the working directory. Or we may want to print '~' for the home directory - // prefix. Or we may want to print dir_path with a trailing '/'. + // This is the default path IO implementation. It is separate to allow + // custom implementations. For example, we may want to print paths as + // relative to the working directory. Or we may want to print '~' for the + // home directory prefix. Or we may want to print dir_path with a trailing + // '/'. // template <typename C, typename K> inline std::basic_ostream<C>& operator<< (std::basic_ostream<C>& os, const basic_path<C, K>& p) { - return os << p.string (); + return to_stream (os, p, false /* representation */); } template <typename C, typename P> @@ -49,6 +50,6 @@ LIBBUTL_MODEXPORT namespace butl { assert (!pn.empty ()); - return os << (pn.name ? *pn.name : pn.path->string ()); + return pn.name ? (os << *pn.name) : (os << *pn.path); } } diff --git a/libbutl/path.ixx b/libbutl/path.ixx index b91102a..165f06a 100644 --- a/libbutl/path.ixx +++ b/libbutl/path.ixx @@ -743,4 +743,28 @@ LIBBUTL_MODEXPORT namespace butl //@@ MOD Clang needs this for some reason. return *this; } + + template <typename C, typename K> + inline std::basic_ostream<C>& + to_stream (std::basic_ostream<C>& os, + const basic_path<C, K>& p, + bool representation) + { + os << p.string (); + + if (representation) + { + C sep (p.separator ()); + +#ifndef _WIN32 + if (sep != 0 && !p.root ()) + os << sep; +#else + if (sep != 0) + os << sep; +#endif + } + + return os; + } } diff --git a/libbutl/path.mxx b/libbutl/path.mxx index 4ed6989..130419c 100644 --- a/libbutl/path.mxx +++ b/libbutl/path.mxx @@ -10,6 +10,7 @@ #ifndef __cpp_lib_modules_ts #include <string> +#include <ostream> #include <cstddef> // ptrdiff_t #include <cstdint> // uint16_t #include <utility> // move(), swap() @@ -1372,6 +1373,12 @@ LIBBUTL_MODEXPORT namespace butl empty () const {return path == nullptr && !name;} }; + template <typename C, typename K> + std::basic_ostream<C>& + to_stream (std::basic_ostream<C>& os, + const basic_path<C, K>& p, + bool representation); + // For operator<< (ostream) see the path-io header. template <typename P> diff --git a/tests/path/driver.cxx b/tests/path/driver.cxx index 72fdf9f..ba25e5b 100644 --- a/tests/path/driver.cxx +++ b/tests/path/driver.cxx @@ -5,6 +5,7 @@ #include <cassert> #ifndef __cpp_lib_modules_ts +#include <sstream> #include <iostream> #include <type_traits> #endif @@ -17,10 +18,10 @@ import std.core; import std.io; #endif import butl.path; -import butl.path_io; +//import butl.path_io; #else #include <libbutl/path.mxx> -#include <libbutl/path-io.mxx> +//#include <libbutl/path-io.mxx> #endif using namespace std; @@ -44,16 +45,31 @@ main () static_assert (is_nothrow_move_constructible<dir_path>::value, ""); #endif - auto test = [] (const char* p, const char* s, const char* r) + auto ts = [] (const path& p, bool representation) + { + ostringstream os; + to_stream (os, p, representation); + return os.str (); + }; + + auto test = [&ts] (const char* p, const char* s, const char* r) { path x (p); - return x.string () == s && x.representation () == r; + + return x.string () == s && + x.representation () == r && + ts (x, false /* representation */) == s && + ts (x, true /* representation */) == r; }; - auto dir_test = [] (const char* p, const char* s, const char* r) + auto dir_test = [&ts] (const char* p, const char* s, const char* r) { dir_path x (p); - return x.string () == s && x.representation () == r; + + return x.string () == s && + x.representation () == r && + ts (x, false /* representation */) == s && + ts (x, true /* representation */) == r; }; #ifndef _WIN32 |