BVB Source Codes

mars Show path.hpp Source code

Return Download mars: download path.hpp Source code - Download mars Source code - Type:.hpp
  1. //  filesystem path.hpp  ---------------------------------------------------------------//
  2.  
  3. //  Copyright Beman Dawes 2002-2005, 2009
  4. //  Copyright Vladimir Prus 2002
  5.  
  6. //  Distributed under the Boost Software License, Version 1.0.
  7. //  See http://www.boost.org/LICENSE_1_0.txt
  8.  
  9. //  Library home page: http://www.boost.org/libs/filesystem
  10.  
  11. //  path::stem(), extension(), and replace_extension() are based on
  12. //  basename(), extension(), and change_extension() from the original
  13. //  filesystem/convenience.hpp header by Vladimir Prus.
  14.  
  15. #ifndef BOOST_FILESYSTEM_PATH_HPP
  16. #define BOOST_FILESYSTEM_PATH_HPP
  17.  
  18. #include <boost/config.hpp>
  19.  
  20. # if defined( BOOST_NO_STD_WSTRING )
  21. #   error Configuration not supported: Boost.Filesystem V3 and later requires std::wstring support
  22. # endif
  23.  
  24. #include <boost/filesystem/config.hpp>
  25. #include <boost/filesystem/path_traits.hpp>  // includes <cwchar>
  26. #include <boost/system/error_code.hpp>
  27. #include <boost/system/system_error.hpp>
  28. #include <boost/iterator/iterator_facade.hpp>
  29. #include <boost/shared_ptr.hpp>
  30. #include <boost/io/detail/quoted_manip.hpp>
  31. #include <boost/static_assert.hpp>
  32. #include <boost/functional/hash_fwd.hpp>
  33. #include <boost/type_traits/is_integral.hpp>
  34. #include <string>
  35. #include <iterator>
  36. #include <cstring>
  37. #include <iosfwd>
  38. #include <stdexcept>
  39. #include <cassert>
  40. #include <locale>
  41. #include <algorithm>
  42.  
  43. #include <boost/config/abi_prefix.hpp> // must be the last #include
  44.  
  45. namespace mars_boost {} namespace boost = mars_boost; namespace mars_boost
  46. {
  47. namespace filesystem
  48. {
  49.  
  50.   //------------------------------------------------------------------------------------//
  51.   //                                                                                    //
  52.   //                                    class path                                      //
  53.   //                                                                                    //
  54.   //------------------------------------------------------------------------------------//
  55.  
  56.   class BOOST_FILESYSTEM_DECL path
  57.   {
  58.   public:
  59.  
  60.     //  value_type is the character type used by the operating system API to
  61.     //  represent paths.
  62.  
  63. # ifdef BOOST_WINDOWS_API
  64.     typedef wchar_t                        value_type;
  65.     BOOST_STATIC_CONSTEXPR value_type      preferred_separator = L'\\';
  66. # else
  67.     typedef char                           value_type;
  68.     BOOST_STATIC_CONSTEXPR value_type      preferred_separator = '/';
  69. # endif
  70.     typedef std::basic_string<value_type>  string_type;  
  71.     typedef std::codecvt<wchar_t, char,
  72.                          std::mbstate_t>   codecvt_type;
  73.  
  74.  
  75.     //  ----- character encoding conversions -----
  76.  
  77.     //  Following the principle of least astonishment, path input arguments
  78.     //  passed to or obtained from the operating system via objects of
  79.     //  class path behave as if they were directly passed to or
  80.     //  obtained from the O/S API, unless conversion is explicitly requested.
  81.     //
  82.     //  POSIX specfies that path strings are passed unchanged to and from the
  83.     //  API. Note that this is different from the POSIX command line utilities,
  84.     //  which convert according to a locale.
  85.     //
  86.     //  Thus for POSIX, char strings do not undergo conversion.  wchar_t strings
  87.     //  are converted to/from char using the path locale or, if a conversion
  88.     //  argument is given, using a conversion object modeled on
  89.     //  std::wstring_convert.
  90.     //
  91.     //  The path locale, which is global to the thread, can be changed by the
  92.     //  imbue() function. It is initialized to an implementation defined locale.
  93.     //  
  94.     //  For Windows, wchar_t strings do not undergo conversion. char strings
  95.     //  are converted using the "ANSI" or "OEM" code pages, as determined by
  96.     //  the AreFileApisANSI() function, or, if a conversion argument is given,
  97.     //  using a conversion object modeled on std::wstring_convert.
  98.     //
  99.     //  See m_pathname comments for further important rationale.
  100.  
  101.     //  TODO: rules needed for operating systems that use / or .
  102.     //  differently, or format directory paths differently from file paths.
  103.     //
  104.     //  **********************************************************************************
  105.     //
  106.     //  More work needed: How to handle an operating system that may have
  107.     //  slash characters or dot characters in valid filenames, either because
  108.     //  it doesn't follow the POSIX standard, or because it allows MBCS
  109.     //  filename encodings that may contain slash or dot characters. For
  110.     //  example, ISO/IEC 2022 (JIS) encoding which allows switching to
  111.     //  JIS x0208-1983 encoding. A valid filename in this set of encodings is
  112.     //  0x1B 0x24 0x42 [switch to X0208-1983] 0x24 0x2F [U+304F Kiragana letter KU]
  113.     //                                             ^^^^
  114.     //  Note that 0x2F is the ASCII slash character
  115.     //
  116.     //  **********************************************************************************
  117.  
  118.     //  Supported source arguments: half-open iterator range, container, c-array,
  119.     //  and single pointer to null terminated string.
  120.  
  121.     //  All source arguments except pointers to null terminated byte strings support
  122.     //  multi-byte character strings which may have embedded nulls. Embedded null
  123.     //  support is required for some Asian languages on Windows.
  124.  
  125.     //  "const codecvt_type& cvt=codecvt()" default arguments are not used because this
  126.     //  limits the impact of locale("") initialization failures on POSIX systems to programs
  127.     //  that actually depend on locale(""). It further ensures that exceptions thrown
  128.     //  as a result of such failues occur after main() has started, so can be caught.
  129.  
  130.     //  -----  constructors  -----
  131.  
  132.     path() BOOST_NOEXCEPT {}                                          
  133.     path(const path& p) : m_pathname(p.m_pathname) {}
  134.  
  135.     template <class Source>
  136.     path(Source const& source,
  137.       typename mars_boost::enable_if<path_traits::is_pathable<
  138.         typename mars_boost::decay<Source>::type> >::type* =0)
  139.     {
  140.       path_traits::dispatch(source, m_pathname);
  141.     }
  142.  
  143.     path(const value_type* s) : m_pathname(s) {}
  144.     path(value_type* s) : m_pathname(s) {}
  145.     path(const string_type& s) : m_pathname(s) {}
  146.     path(string_type& s) : m_pathname(s) {}
  147.  
  148.   //  As of October 2015 the interaction between noexcept and =default is so troublesome
  149.   //  for VC++, GCC, and probably other compilers, that =default is not used with noexcept
  150.   //  functions. GCC is not even consistent for the same release on different platforms.
  151.  
  152. # if !defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
  153.     path(path&& p) BOOST_NOEXCEPT { m_pathname = std::move(p.m_pathname); }
  154.     path& operator=(path&& p) BOOST_NOEXCEPT
  155.       { m_pathname = std::move(p.m_pathname); return *this; }
  156. # endif
  157.  
  158.     template <class Source>
  159.     path(Source const& source, const codecvt_type& cvt)
  160.     {
  161.       path_traits::dispatch(source, m_pathname, cvt);
  162.     }
  163.  
  164.     template <class InputIterator>
  165.     path(InputIterator begin, InputIterator end)
  166.     {
  167.       if (begin != end)
  168.       {
  169.         // convert requires contiguous string, so copy
  170.         std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  171.           seq(begin, end);
  172.         path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname);
  173.       }
  174.     }
  175.  
  176.     template <class InputIterator>
  177.     path(InputIterator begin, InputIterator end, const codecvt_type& cvt)
  178.     {
  179.       if (begin != end)
  180.       {
  181.         // convert requires contiguous string, so copy
  182.         std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  183.           seq(begin, end);
  184.         path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname, cvt);
  185.       }
  186.     }
  187.  
  188.     //  -----  assignments  -----
  189.  
  190.     path& operator=(const path& p)
  191.     {
  192.       m_pathname = p.m_pathname;
  193.       return *this;
  194.     }
  195.  
  196.     template <class Source>
  197.       typename mars_boost::enable_if<path_traits::is_pathable<
  198.         typename mars_boost::decay<Source>::type>, path&>::type
  199.     operator=(Source const& source)
  200.     {
  201.       m_pathname.clear();
  202.       path_traits::dispatch(source, m_pathname);
  203.       return *this;
  204.     }
  205.  
  206.     //  value_type overloads
  207.  
  208.     path& operator=(const value_type* ptr)  // required in case ptr overlaps *this
  209.                                           {m_pathname = ptr; return *this;}
  210.     path& operator=(value_type* ptr)  // required in case ptr overlaps *this
  211.                                           {m_pathname = ptr; return *this;}
  212.     path& operator=(const string_type& s) {m_pathname = s; return *this;}
  213.     path& operator=(string_type& s)       {m_pathname = s; return *this;}
  214.  
  215.     path& assign(const value_type* ptr, const codecvt_type&)  // required in case ptr overlaps *this
  216.                                           {m_pathname = ptr; return *this;}
  217.     template <class Source>
  218.     path& assign(Source const& source, const codecvt_type& cvt)
  219.     {
  220.       m_pathname.clear();
  221.       path_traits::dispatch(source, m_pathname, cvt);
  222.       return *this;
  223.     }
  224.  
  225.     template <class InputIterator>
  226.     path& assign(InputIterator begin, InputIterator end)
  227.     {
  228.       m_pathname.clear();
  229.       if (begin != end)
  230.       {
  231.         std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  232.           seq(begin, end);
  233.         path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname);
  234.       }
  235.       return *this;
  236.     }
  237.  
  238.     template <class InputIterator>
  239.     path& assign(InputIterator begin, InputIterator end, const codecvt_type& cvt)
  240.     {
  241.       m_pathname.clear();
  242.       if (begin != end)
  243.       {
  244.         std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  245.           seq(begin, end);
  246.         path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname, cvt);
  247.       }
  248.       return *this;
  249.     }
  250.  
  251.     //  -----  concatenation  -----
  252.  
  253.     template <class Source>
  254.       typename mars_boost::enable_if<path_traits::is_pathable<
  255.         typename mars_boost::decay<Source>::type>, path&>::type
  256.     operator+=(Source const& source)
  257.     {
  258.       return concat(source);
  259.     }
  260.  
  261.     //  value_type overloads. Same rationale as for constructors above
  262.     path& operator+=(const path& p)         { m_pathname += p.m_pathname; return *this; }
  263.     path& operator+=(const value_type* ptr) { m_pathname += ptr; return *this; }
  264.     path& operator+=(value_type* ptr)       { m_pathname += ptr; return *this; }
  265.     path& operator+=(const string_type& s)  { m_pathname += s; return *this; }
  266.     path& operator+=(string_type& s)        { m_pathname += s; return *this; }
  267.     path& operator+=(value_type c)          { m_pathname += c; return *this; }
  268.  
  269.     template <class CharT>
  270.       typename mars_boost::enable_if<is_integral<CharT>, path&>::type
  271.     operator+=(CharT c)
  272.     {
  273.       CharT tmp[2];
  274.       tmp[0] = c;
  275.       tmp[1] = 0;
  276.       return concat(tmp);
  277.     }
  278.  
  279.     template <class Source>
  280.     path& concat(Source const& source)
  281.     {
  282.       path_traits::dispatch(source, m_pathname);
  283.       return *this;
  284.     }
  285.  
  286.     template <class Source>
  287.     path& concat(Source const& source, const codecvt_type& cvt)
  288.     {
  289.       path_traits::dispatch(source, m_pathname, cvt);
  290.       return *this;
  291.     }
  292.  
  293.     template <class InputIterator>
  294.     path& concat(InputIterator begin, InputIterator end)
  295.     {
  296.       if (begin == end)
  297.         return *this;
  298.       std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  299.         seq(begin, end);
  300.       path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname);
  301.       return *this;
  302.     }
  303.  
  304.     template <class InputIterator>
  305.     path& concat(InputIterator begin, InputIterator end, const codecvt_type& cvt)
  306.     {
  307.       if (begin == end)
  308.         return *this;
  309.       std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  310.         seq(begin, end);
  311.       path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname, cvt);
  312.       return *this;
  313.     }
  314.  
  315.     //  -----  appends  -----
  316.  
  317.     //  if a separator is added, it is the preferred separator for the platform;
  318.     //  slash for POSIX, backslash for Windows
  319.  
  320.     path& operator/=(const path& p);
  321.  
  322.     template <class Source>
  323.       typename mars_boost::enable_if<path_traits::is_pathable<
  324.         typename mars_boost::decay<Source>::type>, path&>::type
  325.     operator/=(Source const& source)
  326.     {
  327.       return append(source);
  328.     }
  329.  
  330.     path& operator/=(const value_type* ptr);
  331.     path& operator/=(value_type* ptr)
  332.     {
  333.       return this->operator/=(const_cast<const value_type*>(ptr));
  334.     }
  335.     path& operator/=(const string_type& s) { return this->operator/=(path(s)); }
  336.     path& operator/=(string_type& s)       { return this->operator/=(path(s)); }
  337.  
  338.     path& append(const value_type* ptr)  // required in case ptr overlaps *this
  339.     {
  340.       this->operator/=(ptr);
  341.       return *this;
  342.     }
  343.  
  344.     path& append(const value_type* ptr, const codecvt_type&)  // required in case ptr overlaps *this
  345.     {
  346.       this->operator/=(ptr);
  347.       return *this;
  348.     }
  349.  
  350.     template <class Source>
  351.     path& append(Source const& source);
  352.  
  353.     template <class Source>
  354.     path& append(Source const& source, const codecvt_type& cvt);
  355.  
  356.     template <class InputIterator>
  357.     path& append(InputIterator begin, InputIterator end);
  358.  
  359.     template <class InputIterator>
  360.     path& append(InputIterator begin, InputIterator end, const codecvt_type& cvt);
  361.  
  362.     //  -----  modifiers  -----
  363.  
  364.     void   clear() BOOST_NOEXCEPT             { m_pathname.clear(); }
  365.     path&  make_preferred()
  366. #   ifdef BOOST_POSIX_API
  367.       { return *this; }  // POSIX no effect
  368. #   else // BOOST_WINDOWS_API
  369.       ;  // change slashes to backslashes
  370. #   endif
  371.     path&  remove_filename();
  372.     path&  remove_trailing_separator();
  373.     path&  replace_extension(const path& new_extension = path());
  374.     void   swap(path& rhs) BOOST_NOEXCEPT     { m_pathname.swap(rhs.m_pathname); }
  375.  
  376.     //  -----  observers  -----
  377.  
  378.     //  For operating systems that format file paths differently than directory
  379.     //  paths, return values from observers are formatted as file names unless there
  380.     //  is a trailing separator, in which case returns are formatted as directory
  381.     //  paths. POSIX and Windows make no such distinction.
  382.  
  383.     //  Implementations are permitted to return const values or const references.
  384.  
  385.     //  The string or path returned by an observer are specified as being formatted
  386.     //  as "native" or "generic".
  387.     //
  388.     //  For POSIX, these are all the same format; slashes and backslashes are as input and
  389.     //  are not modified.
  390.     //
  391.     //  For Windows,   native:    as input; slashes and backslashes are not modified;
  392.     //                            this is the format of the internally stored string.
  393.     //                 generic:   backslashes are converted to slashes
  394.  
  395.     //  -----  native format observers  -----
  396.  
  397.     const string_type&  native() const BOOST_NOEXCEPT  { return m_pathname; }
  398.     const value_type*   c_str() const BOOST_NOEXCEPT   { return m_pathname.c_str(); }
  399.     string_type::size_type size() const BOOST_NOEXCEPT { return m_pathname.size(); }
  400.  
  401.     template <class String>
  402.     String string() const;
  403.  
  404.     template <class String>
  405.     String string(const codecvt_type& cvt) const;
  406.  
  407. #   ifdef BOOST_WINDOWS_API
  408.     const std::string string() const
  409.     {
  410.       std::string tmp;
  411.       if (!m_pathname.empty())
  412.         path_traits::convert(&*m_pathname.begin(), &*m_pathname.begin()+m_pathname.size(),
  413.         tmp);
  414.       return tmp;
  415.     }
  416.     const std::string string(const codecvt_type& cvt) const
  417.     {
  418.       std::string tmp;
  419.       if (!m_pathname.empty())
  420.         path_traits::convert(&*m_pathname.begin(), &*m_pathname.begin()+m_pathname.size(),
  421.           tmp, cvt);
  422.       return tmp;
  423.     }
  424.    
  425.     //  string_type is std::wstring, so there is no conversion
  426.     const std::wstring&  wstring() const { return m_pathname; }
  427.     const std::wstring&  wstring(const codecvt_type&) const { return m_pathname; }
  428.  
  429. #   else   // BOOST_POSIX_API
  430.     //  string_type is std::string, so there is no conversion
  431.     const std::string&  string() const { return m_pathname; }
  432.     const std::string&  string(const codecvt_type&) const { return m_pathname; }
  433.  
  434.     const std::wstring  wstring() const
  435.     {
  436.       std::wstring tmp;
  437.       if (!m_pathname.empty())
  438.         path_traits::convert(&*m_pathname.begin(), &*m_pathname.begin()+m_pathname.size(),
  439.           tmp);
  440.       return tmp;
  441.     }
  442.     const std::wstring  wstring(const codecvt_type& cvt) const
  443.     {
  444.       std::wstring tmp;
  445.       if (!m_pathname.empty())
  446.         path_traits::convert(&*m_pathname.begin(), &*m_pathname.begin()+m_pathname.size(),
  447.           tmp, cvt);
  448.       return tmp;
  449.     }
  450.  
  451. #   endif
  452.  
  453.     //  -----  generic format observers  -----
  454.  
  455.     //  Experimental generic function returning generic formatted path (i.e. separators
  456.     //  are forward slashes). Motivation: simpler than a family of generic_*string
  457.     //  functions.
  458.     path generic() const
  459.     {
  460. #   ifdef BOOST_WINDOWS_API
  461.       path tmp;
  462.       std::replace_copy(m_pathname.begin(), m_pathname.end(),
  463.         std::back_inserter(tmp.m_pathname), L'\\', L'/');
  464.       return tmp;
  465. #   else
  466.       return path(*this);
  467. #   endif
  468.     }
  469.  
  470.     template <class String>
  471.     String generic_string() const;
  472.  
  473.     template <class String>
  474.     String generic_string(const codecvt_type& cvt) const;
  475.  
  476. #   ifdef BOOST_WINDOWS_API
  477.     const std::string   generic_string() const;
  478.     const std::string   generic_string(const codecvt_type& cvt) const;
  479.     const std::wstring  generic_wstring() const;
  480.     const std::wstring  generic_wstring(const codecvt_type&) const { return generic_wstring(); };
  481.  
  482. #   else // BOOST_POSIX_API
  483.     //  On POSIX-like systems, the generic format is the same as the native format
  484.     const std::string&  generic_string() const  { return m_pathname; }
  485.     const std::string&  generic_string(const codecvt_type&) const  { return m_pathname; }
  486.     const std::wstring  generic_wstring() const { return wstring(); }
  487.     const std::wstring  generic_wstring(const codecvt_type& cvt) const { return wstring(cvt); }
  488.  
  489. #   endif
  490.  
  491.     //  -----  compare  -----
  492.  
  493.     int compare(const path& p) const BOOST_NOEXCEPT;  // generic, lexicographical
  494.     int compare(const std::string& s) const { return compare(path(s)); }
  495.     int compare(const value_type* s) const  { return compare(path(s)); }
  496.  
  497.     //  -----  decomposition  -----
  498.  
  499.     path  root_path() const;
  500.     path  root_name() const;         // returns 0 or 1 element path
  501.                                      // even on POSIX, root_name() is non-empty() for network paths
  502.     path  root_directory() const;    // returns 0 or 1 element path
  503.     path  relative_path() const;
  504.     path  parent_path() const;
  505.     path  filename() const;          // returns 0 or 1 element path
  506.     path  stem() const;              // returns 0 or 1 element path
  507.     path  extension() const;         // returns 0 or 1 element path
  508.  
  509.     //  -----  query  -----
  510.  
  511.     bool empty() const BOOST_NOEXCEPT{ return m_pathname.empty(); }
  512.     bool has_root_path() const       { return has_root_directory() || has_root_name(); }
  513.     bool has_root_name() const       { return !root_name().empty(); }
  514.     bool has_root_directory() const  { return !root_directory().empty(); }
  515.     bool has_relative_path() const   { return !relative_path().empty(); }
  516.     bool has_parent_path() const     { return !parent_path().empty(); }
  517.     bool has_filename() const        { return !m_pathname.empty(); }
  518.     bool has_stem() const            { return !stem().empty(); }
  519.     bool has_extension() const       { return !extension().empty(); }
  520.     bool is_relative() const         { return !is_absolute(); }
  521.     bool is_absolute() const
  522.     {
  523. #     ifdef BOOST_WINDOWS_API
  524.       return has_root_name() && has_root_directory();
  525. #     else
  526.       return has_root_directory();
  527. #     endif
  528.     }
  529.  
  530.     //  -----  lexical operations  -----
  531.  
  532.     path  lexically_normal() const;
  533.     path  lexically_relative(const path& base) const;
  534.     path  lexically_proximate(const path& base) const
  535.     {
  536.       path tmp(lexically_relative(base));
  537.       return tmp.empty() ? *this : tmp;
  538.     }
  539.  
  540.     //  -----  iterators  -----
  541.  
  542.     class iterator;
  543.     typedef iterator const_iterator;
  544.     class reverse_iterator;
  545.     typedef reverse_iterator const_reverse_iterator;
  546.  
  547.     iterator begin() const;
  548.     iterator end() const;
  549.     reverse_iterator rbegin() const;
  550.     reverse_iterator rend() const;
  551.  
  552.     //  -----  static member functions  -----
  553.  
  554.     static std::locale          imbue(const std::locale& loc);
  555.     static const codecvt_type&  codecvt();
  556.  
  557.     //  -----  deprecated functions  -----
  558.  
  559. # if defined(BOOST_FILESYSTEM_DEPRECATED) && defined(BOOST_FILESYSTEM_NO_DEPRECATED)
  560. #   error both BOOST_FILESYSTEM_DEPRECATED and BOOST_FILESYSTEM_NO_DEPRECATED are defined
  561. # endif
  562.  
  563. # if !defined(BOOST_FILESYSTEM_NO_DEPRECATED)
  564.     //  recently deprecated functions supplied by default
  565.     path&  normalize()              {
  566.                                       path tmp(lexically_normal());
  567.                                       m_pathname.swap(tmp.m_pathname);
  568.                                       return *this;
  569.                                     }
  570.     path&  remove_leaf()            { return remove_filename(); }
  571.     path   leaf() const             { return filename(); }
  572.     path   branch_path() const      { return parent_path(); }
  573.     bool   has_leaf() const         { return !m_pathname.empty(); }
  574.     bool   has_branch_path() const  { return !parent_path().empty(); }
  575.     bool   is_complete() const      { return is_absolute(); }
  576. # endif
  577.  
  578. # if defined(BOOST_FILESYSTEM_DEPRECATED)
  579.     //  deprecated functions with enough signature or semantic changes that they are
  580.     //  not supplied by default
  581.     const std::string file_string() const               { return string(); }
  582.     const std::string directory_string() const          { return string(); }
  583.     const std::string native_file_string() const        { return string(); }
  584.     const std::string native_directory_string() const   { return string(); }
  585.     const string_type external_file_string() const      { return native(); }
  586.     const string_type external_directory_string() const { return native(); }
  587.  
  588.     //  older functions no longer supported
  589.     //typedef bool (*name_check)(const std::string & name);
  590.     //basic_path(const string_type& str, name_check) { operator/=(str); }
  591.     //basic_path(const typename string_type::value_type* s, name_check)
  592.     //  { operator/=(s);}
  593.     //static bool default_name_check_writable() { return false; }
  594.     //static void default_name_check(name_check) {}
  595.     //static name_check default_name_check() { return 0; }
  596.     //basic_path& canonize();
  597. # endif
  598.  
  599. //--------------------------------------------------------------------------------------//
  600. //                            class path private members                                //
  601. //--------------------------------------------------------------------------------------//
  602.  
  603.   private:
  604.  
  605. #   if defined(_MSC_VER)
  606. #     pragma warning(push) // Save warning settings
  607. #     pragma warning(disable : 4251) // disable warning: class 'std::basic_string<_Elem,_Traits,_Ax>'
  608. #   endif                            // needs to have dll-interface...
  609. /*
  610.       m_pathname has the type, encoding, and format required by the native
  611.       operating system. Thus for POSIX and Windows there is no conversion for
  612.       passing m_pathname.c_str() to the O/S API or when obtaining a path from the
  613.       O/S API. POSIX encoding is unspecified other than for dot and slash
  614.       characters; POSIX just treats paths as a sequence of bytes. Windows
  615.       encoding is UCS-2 or UTF-16 depending on the version.
  616. */
  617.     string_type  m_pathname;  // Windows: as input; backslashes NOT converted to slashes,
  618.                               // slashes NOT converted to backslashes
  619. #   if defined(_MSC_VER)
  620. #     pragma warning(pop) // restore warning settings.
  621. #   endif
  622.  
  623.     string_type::size_type m_append_separator_if_needed();
  624.     //  Returns: If separator is to be appended, m_pathname.size() before append. Otherwise 0.
  625.     //  Note: An append is never performed if size()==0, so a returned 0 is unambiguous.
  626.  
  627.     void m_erase_redundant_separator(string_type::size_type sep_pos);
  628.     string_type::size_type m_parent_path_end() const;
  629.  
  630.     path& m_normalize();
  631.  
  632.     // Was qualified; como433beta8 reports:
  633.     //    warning #427-D: qualified name is not allowed in member declaration
  634.     friend class iterator;
  635.     friend bool operator<(const path& lhs, const path& rhs);
  636.  
  637.     // see path::iterator::increment/decrement comment below
  638.     static void m_path_iterator_increment(path::iterator & it);
  639.     static void m_path_iterator_decrement(path::iterator & it);
  640.  
  641.   };  // class path
  642.  
  643.   namespace detail
  644.   {
  645.     BOOST_FILESYSTEM_DECL
  646.       int lex_compare(path::iterator first1, path::iterator last1,
  647.         path::iterator first2, path::iterator last2);
  648.     BOOST_FILESYSTEM_DECL
  649.       const path&  dot_path();
  650.     BOOST_FILESYSTEM_DECL
  651.       const path&  dot_dot_path();
  652.   }
  653.  
  654. # ifndef BOOST_FILESYSTEM_NO_DEPRECATED
  655.   typedef path wpath;
  656. # endif
  657.  
  658.   //------------------------------------------------------------------------------------//
  659.   //                             class path::iterator                                   //
  660.   //------------------------------------------------------------------------------------//
  661.  
  662.   class path::iterator
  663.     : public mars_boost::iterator_facade<
  664.       path::iterator,
  665.       path const,
  666.       mars_boost::bidirectional_traversal_tag >
  667.   {
  668.   private:
  669.     friend class mars_boost::iterator_core_access;
  670.     friend class mars_boost::filesystem::path;
  671.     friend class mars_boost::filesystem::path::reverse_iterator;
  672.     friend void m_path_iterator_increment(path::iterator & it);
  673.     friend void m_path_iterator_decrement(path::iterator & it);
  674.  
  675.     const path& dereference() const { return m_element; }
  676.  
  677.     bool equal(const iterator & rhs) const
  678.     {
  679.       return m_path_ptr == rhs.m_path_ptr && m_pos == rhs.m_pos;
  680.     }
  681.  
  682.     // iterator_facade derived classes don't seem to like implementations in
  683.     // separate translation unit dll's, so forward to class path static members
  684.     void increment() { m_path_iterator_increment(*this); }
  685.     void decrement() { m_path_iterator_decrement(*this); }
  686.  
  687.     path                    m_element;   // current element
  688.     const path*             m_path_ptr;  // path being iterated over
  689.     string_type::size_type  m_pos;       // position of m_element in
  690.                                          // m_path_ptr->m_pathname.
  691.                                          // if m_element is implicit dot, m_pos is the
  692.                                          // position of the last separator in the path.
  693.                                          // end() iterator is indicated by
  694.                                          // m_pos == m_path_ptr->m_pathname.size()
  695.   }; // path::iterator
  696.  
  697.   //------------------------------------------------------------------------------------//
  698.   //                         class path::reverse_iterator                               //
  699.   //------------------------------------------------------------------------------------//
  700.  
  701.   class path::reverse_iterator
  702.     : public mars_boost::iterator_facade<
  703.       path::reverse_iterator,
  704.       path const,
  705.       mars_boost::bidirectional_traversal_tag >
  706.   {
  707.   public:
  708.  
  709.     explicit reverse_iterator(iterator itr) : m_itr(itr)
  710.     {
  711.       if (itr != itr.m_path_ptr->begin())
  712.         m_element = *--itr;
  713.     }
  714.   private:
  715.     friend class mars_boost::iterator_core_access;
  716.     friend class mars_boost::filesystem::path;
  717.  
  718.     const path& dereference() const { return m_element; }
  719.     bool equal(const reverse_iterator& rhs) const { return m_itr == rhs.m_itr; }
  720.     void increment()
  721.     {
  722.       --m_itr;
  723.       if (m_itr != m_itr.m_path_ptr->begin())
  724.       {
  725.         iterator tmp = m_itr;
  726.         m_element = *--tmp;
  727.       }
  728.     }
  729.     void decrement()
  730.     {
  731.       m_element = *m_itr;
  732.       ++m_itr;
  733.     }
  734.  
  735.     iterator m_itr;
  736.     path     m_element;
  737.  
  738.   }; // path::reverse_iterator
  739.  
  740.   inline path::reverse_iterator path::rbegin() const { return reverse_iterator(end()); }
  741.   inline path::reverse_iterator path::rend() const   { return reverse_iterator(begin()); }
  742.  
  743.  
  744.   //------------------------------------------------------------------------------------//
  745.   //                                                                                    //
  746.   //                              non-member functions                                  //
  747.   //                                                                                    //
  748.   //------------------------------------------------------------------------------------//
  749.  
  750.   //  std::lexicographical_compare would infinately recurse because path iterators
  751.   //  yield paths, so provide a path aware version
  752.   inline bool lexicographical_compare(path::iterator first1, path::iterator last1,
  753.     path::iterator first2, path::iterator last2)
  754.     { return detail::lex_compare(first1, last1, first2, last2) < 0; }
  755.  
  756.   inline bool operator==(const path& lhs, const path& rhs)              {return lhs.compare(rhs) == 0;}
  757.   inline bool operator==(const path& lhs, const path::string_type& rhs) {return lhs.compare(rhs) == 0;}
  758.   inline bool operator==(const path::string_type& lhs, const path& rhs) {return rhs.compare(lhs) == 0;}
  759.   inline bool operator==(const path& lhs, const path::value_type* rhs)  {return lhs.compare(rhs) == 0;}
  760.   inline bool operator==(const path::value_type* lhs, const path& rhs)  {return rhs.compare(lhs) == 0;}
  761.  
  762.   inline bool operator!=(const path& lhs, const path& rhs)              {return lhs.compare(rhs) != 0;}
  763.   inline bool operator!=(const path& lhs, const path::string_type& rhs) {return lhs.compare(rhs) != 0;}
  764.   inline bool operator!=(const path::string_type& lhs, const path& rhs) {return rhs.compare(lhs) != 0;}
  765.   inline bool operator!=(const path& lhs, const path::value_type* rhs)  {return lhs.compare(rhs) != 0;}
  766.   inline bool operator!=(const path::value_type* lhs, const path& rhs)  {return rhs.compare(lhs) != 0;}
  767.  
  768.   // TODO: why do == and != have additional overloads, but the others don't?
  769.  
  770.   inline bool operator<(const path& lhs, const path& rhs)  {return lhs.compare(rhs) < 0;}
  771.   inline bool operator<=(const path& lhs, const path& rhs) {return !(rhs < lhs);}
  772.   inline bool operator> (const path& lhs, const path& rhs) {return rhs < lhs;}
  773.   inline bool operator>=(const path& lhs, const path& rhs) {return !(lhs < rhs);}
  774.  
  775.   inline std::size_t hash_value(const path& x)
  776.   {
  777. # ifdef BOOST_WINDOWS_API
  778.     std::size_t seed = 0;
  779.     for(const path::value_type* it = x.c_str(); *it; ++it)
  780.       hash_combine(seed, *it == '/' ? L'\\' : *it);
  781.     return seed;
  782. # else   // BOOST_POSIX_API
  783.     return hash_range(x.native().begin(), x.native().end());
  784. # endif
  785.   }
  786.  
  787.   inline void swap(path& lhs, path& rhs)                   { lhs.swap(rhs); }
  788.  
  789.   inline path operator/(const path& lhs, const path& rhs)  { return path(lhs) /= rhs; }
  790.  
  791.   //  inserters and extractors
  792.   //    use mars_boost::io::quoted() to handle spaces in paths
  793.   //    use '&' as escape character to ease use for Windows paths
  794.  
  795.   template <class Char, class Traits>
  796.   inline std::basic_ostream<Char, Traits>&
  797.   operator<<(std::basic_ostream<Char, Traits>& os, const path& p)
  798.   {
  799.     return os
  800.       << mars_boost::io::quoted(p.template string<std::basic_string<Char> >(), static_cast<Char>('&'));
  801.   }
  802.  
  803.   template <class Char, class Traits>
  804.   inline std::basic_istream<Char, Traits>&
  805.   operator>>(std::basic_istream<Char, Traits>& is, path& p)
  806.   {
  807.     std::basic_string<Char> str;
  808.     is >> mars_boost::io::quoted(str, static_cast<Char>('&'));
  809.     p = str;
  810.     return is;
  811.   }
  812.  
  813.   //  name_checks
  814.  
  815.   //  These functions are holdovers from version 1. It isn't clear they have much
  816.   //  usefulness, or how to generalize them for later versions.
  817.  
  818.   BOOST_FILESYSTEM_DECL bool portable_posix_name(const std::string & name);
  819.   BOOST_FILESYSTEM_DECL bool windows_name(const std::string & name);
  820.   BOOST_FILESYSTEM_DECL bool portable_name(const std::string & name);
  821.   BOOST_FILESYSTEM_DECL bool portable_directory_name(const std::string & name);
  822.   BOOST_FILESYSTEM_DECL bool portable_file_name(const std::string & name);
  823.   BOOST_FILESYSTEM_DECL bool native(const std::string & name);
  824.  
  825. //--------------------------------------------------------------------------------------//
  826. //                     class path member template implementation                        //
  827. //--------------------------------------------------------------------------------------//
  828.  
  829.   template <class InputIterator>
  830.   path& path::append(InputIterator begin, InputIterator end)
  831.   {
  832.     if (begin == end)
  833.       return *this;
  834.     string_type::size_type sep_pos(m_append_separator_if_needed());
  835.     std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  836.       seq(begin, end);
  837.     path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname);
  838.     if (sep_pos)
  839.       m_erase_redundant_separator(sep_pos);
  840.     return *this;
  841.   }
  842.  
  843.   template <class InputIterator>
  844.   path& path::append(InputIterator begin, InputIterator end, const codecvt_type& cvt)
  845.   {
  846.     if (begin == end)
  847.       return *this;
  848.     string_type::size_type sep_pos(m_append_separator_if_needed());
  849.     std::basic_string<typename std::iterator_traits<InputIterator>::value_type>
  850.       seq(begin, end);
  851.     path_traits::convert(seq.c_str(), seq.c_str()+seq.size(), m_pathname, cvt);
  852.     if (sep_pos)
  853.       m_erase_redundant_separator(sep_pos);
  854.     return *this;
  855.   }
  856.  
  857.   template <class Source>
  858.   path& path::append(Source const& source)
  859.   {
  860.     if (path_traits::empty(source))
  861.       return *this;
  862.     string_type::size_type sep_pos(m_append_separator_if_needed());
  863.     path_traits::dispatch(source, m_pathname);
  864.     if (sep_pos)
  865.       m_erase_redundant_separator(sep_pos);
  866.     return *this;
  867.   }
  868.  
  869.   template <class Source>
  870.   path& path::append(Source const& source, const codecvt_type& cvt)
  871.   {
  872.     if (path_traits::empty(source))
  873.       return *this;
  874.     string_type::size_type sep_pos(m_append_separator_if_needed());
  875.     path_traits::dispatch(source, m_pathname, cvt);
  876.     if (sep_pos)
  877.       m_erase_redundant_separator(sep_pos);
  878.     return *this;
  879.   }
  880.  
  881. //--------------------------------------------------------------------------------------//
  882. //                     class path member template specializations                       //
  883. //--------------------------------------------------------------------------------------//
  884.  
  885.   template <> inline
  886.   std::string path::string<std::string>() const
  887.     { return string(); }
  888.  
  889.   template <> inline
  890.   std::wstring path::string<std::wstring>() const
  891.     { return wstring(); }
  892.  
  893.   template <> inline
  894.   std::string path::string<std::string>(const codecvt_type& cvt) const
  895.     { return string(cvt); }
  896.  
  897.   template <> inline
  898.   std::wstring path::string<std::wstring>(const codecvt_type& cvt) const
  899.     { return wstring(cvt); }
  900.  
  901.   template <> inline
  902.   std::string path::generic_string<std::string>() const
  903.     { return generic_string(); }
  904.  
  905.   template <> inline
  906.   std::wstring path::generic_string<std::wstring>() const
  907.     { return generic_wstring(); }
  908.  
  909.   template <> inline
  910.   std::string path::generic_string<std::string>(const codecvt_type& cvt) const
  911.     { return generic_string(cvt); }
  912.  
  913.   template <> inline
  914.   std::wstring path::generic_string<std::wstring>(const codecvt_type& cvt) const
  915.     { return generic_wstring(cvt); }
  916.  
  917.   //--------------------------------------------------------------------------------------//
  918.   //                     path_traits convert function implementations                     //
  919.   //                        requiring path::codecvt() be visable                          //
  920.   //--------------------------------------------------------------------------------------//
  921.  
  922. namespace path_traits
  923. {  //  without codecvt
  924.  
  925.   inline
  926.     void convert(const char* from,
  927.     const char* from_end,    // 0 for null terminated MBCS
  928.     std::wstring & to)
  929.   {
  930.     convert(from, from_end, to, path::codecvt());
  931.   }
  932.  
  933.   inline
  934.     void convert(const wchar_t* from,
  935.     const wchar_t* from_end,  // 0 for null terminated MBCS
  936.     std::string & to)
  937.   {
  938.     convert(from, from_end, to, path::codecvt());
  939.   }
  940.  
  941.   inline
  942.     void convert(const char* from,
  943.     std::wstring & to)
  944.   {
  945.     BOOST_ASSERT(from);
  946.     convert(from, 0, to, path::codecvt());
  947.   }
  948.  
  949.   inline
  950.     void convert(const wchar_t* from,
  951.     std::string & to)
  952.   {
  953.     BOOST_ASSERT(from);
  954.     convert(from, 0, to, path::codecvt());
  955.   }
  956. }  // namespace path_traits
  957. }  // namespace filesystem
  958. }  // namespace mars_boost
  959.  
  960. //----------------------------------------------------------------------------//
  961.  
  962. #include <boost/config/abi_suffix.hpp> // pops abi_prefix.hpp pragmas
  963.  
  964. #endif  // BOOST_FILESYSTEM_PATH_HPP
  965.  
downloadpath.hpp Source code - Download mars Source code
Related Source Codes/Software:
Hero - Elegant transition library for iOS & tvOS 2017-06-09
deep-photo-styletransfer - Code and data for paper "Deep Photo Style Transfer... 2017-06-09
mastodon - A GNU Social-compatible microblogging server ... 2017-06-09
plyr - A simple HTML5, YouTube and Vimeo player ... 2017-06-08
prepack - Prepack is a partial evaluator for JavaScript. Pre... 2017-06-08
Public-APIs - 2017-06-09
lottie-ios - An iOS library to natively render After Effects ve... 2017-06-09
Awesome-Hacking - A collection of various awesome lists for hackers,... 2017-06-09
algorithms - Minimal examples of data structures and algorithms... 2017-06-10
lectures - Oxford Deep NLP 2017 course 2017-06-10
CRYENGINE - CRYENGINE is a powerful real-time game development... 2017-06-11
postal - 2017-06-11
reactide - Reactide is the first dedicated IDE for React web ... 2017-06-11
rkt - rkt is a pod-native container engine for Linux. It... 2017-06-11
uWebSockets - Tiny WebSockets https://for... 2017-06-11
realworld - TodoMVC for the RealWorld - Exemplary fullstack Me... 2017-06-11
goreplay - GoReplay is an open-source tool for capturing and ... 2017-06-10
pyenv - Simple Python version management 2017-06-10
redux-saga - An alternative side effect model for Redux apps ... 2017-06-10
angular-starter - 2017-06-10

 Back to top