You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

237 lines
9.0 KiB

  1. /* /////////////////////////////////////////////////////////////////////////
  2. * File: unixstl/filesystem/functionals.hpp
  3. *
  4. * Purpose: A number of useful functionals .
  5. *
  6. * Created: 2nd November 2003
  7. * Updated: 10th August 2009
  8. *
  9. * Home: http://stlsoft.org/
  10. *
  11. * Copyright (c) 2003-2009, Matthew Wilson and Synesis Software
  12. * All rights reserved.
  13. *
  14. * Redistribution and use in source and binary forms, with or without
  15. * modification, are permitted provided that the following conditions are met:
  16. *
  17. * - Redistributions of source code must retain the above copyright notice, this
  18. * list of conditions and the following disclaimer.
  19. * - Redistributions in binary form must reproduce the above copyright notice,
  20. * this list of conditions and the following disclaimer in the documentation
  21. * and/or other materials provided with the distribution.
  22. * - Neither the name(s) of Matthew Wilson and Synesis Software nor the names of
  23. * any contributors may be used to endorse or promote products derived from
  24. * this software without specific prior written permission.
  25. *
  26. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  27. * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  28. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  29. * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
  30. * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
  31. * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
  32. * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
  33. * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
  34. * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  35. * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  36. * POSSIBILITY OF SUCH DAMAGE.
  37. *
  38. * ////////////////////////////////////////////////////////////////////// */
  39. /** \file unixstl/filesystem/functionals.hpp
  40. *
  41. * \brief [C++ only] Definition of filesystem function classes, including
  42. * unixstl::path_compare and unixstl::path_exists
  43. * (\ref group__library__filesystem "File System" Library).
  44. */
  45. #ifndef UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS
  46. #define UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS
  47. #ifndef STLSOFT_DOCUMENTATION_SKIP_SECTION
  48. # define UNIXSTL_VER_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS_MAJOR 4
  49. # define UNIXSTL_VER_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS_MINOR 1
  50. # define UNIXSTL_VER_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS_REVISION 2
  51. # define UNIXSTL_VER_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS_EDIT 48
  52. #endif /* !STLSOFT_DOCUMENTATION_SKIP_SECTION */
  53. /* /////////////////////////////////////////////////////////////////////////
  54. * Includes
  55. */
  56. #ifndef UNIXSTL_INCL_UNIXSTL_H_UNIXSTL
  57. # include <unixstl/unixstl.h>
  58. #endif /* !UNIXSTL_INCL_UNIXSTL_H_UNIXSTL */
  59. #ifndef STLSOFT_INCL_STLSOFT_SHIMS_ACCESS_HPP_STRING
  60. # include <stlsoft/shims/access/string.hpp>
  61. #endif /* !STLSOFT_INCL_STLSOFT_SHIMS_ACCESS_HPP_STRING */
  62. #ifndef UNIXSTL_INCL_UNIXSTL_SHIMS_ACCESS_HPP_STRING
  63. # include <unixstl/shims/access/string.hpp>
  64. #endif /* !UNIXSTL_INCL_UNIXSTL_SHIMS_ACCESS_HPP_STRING */
  65. #ifndef UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_TRAITS
  66. # include <unixstl/filesystem/filesystem_traits.hpp>
  67. #endif /* !UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_TRAITS */
  68. #ifndef UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILE_PATH_BUFFER
  69. # include <unixstl/filesystem/file_path_buffer.hpp>
  70. #endif /* !UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILE_PATH_BUFFER */
  71. #ifndef _UNIXSTL_FUNCTIONALS_NO_STD
  72. # include <functional>
  73. #else /* ? _UNIXSTL_FUNCTIONALS_NO_STD */
  74. # error Now need to write that std_binary_function stuff!!
  75. #endif /* _UNIXSTL_FUNCTIONALS_NO_STD */
  76. /* /////////////////////////////////////////////////////////////////////////
  77. * Namespace
  78. */
  79. #ifndef _UNIXSTL_NO_NAMESPACE
  80. # if defined(_STLSOFT_NO_NAMESPACE) || \
  81. defined(STLSOFT_DOCUMENTATION_SKIP_SECTION)
  82. /* There is no stlsoft namespace, so must define ::unixstl */
  83. namespace unixstl
  84. {
  85. # else
  86. /* Define stlsoft::unixstl_project */
  87. namespace stlsoft
  88. {
  89. namespace unixstl_project
  90. {
  91. # endif /* _STLSOFT_NO_NAMESPACE */
  92. #endif /* !_UNIXSTL_NO_NAMESPACE */
  93. /* /////////////////////////////////////////////////////////////////////////
  94. * Classes
  95. */
  96. /** \brief A function class that compares two file-system paths
  97. *
  98. * \ingroup group__library__filesystem
  99. */
  100. template <ss_typename_param_k C>
  101. // [[synesis:class:function-class:binary-predicate: path_compare<T<C>>]]
  102. struct path_compare
  103. : public unixstl_ns_qual_std(binary_function)<C const*, C const*, us_bool_t>
  104. {
  105. public:
  106. /// \brief The character type
  107. typedef C char_type;
  108. private:
  109. typedef unixstl_ns_qual_std(binary_function)<C const*, C const*, us_bool_t> parent_class_type;
  110. public:
  111. /// \brief The first argument type
  112. typedef ss_typename_type_k parent_class_type::first_argument_type first_argument_type;
  113. /// \brief The second argument type
  114. typedef ss_typename_type_k parent_class_type::second_argument_type second_argument_type;
  115. /// \brief The result type
  116. typedef ss_typename_type_k parent_class_type::result_type result_type;
  117. /// \brief The traits type
  118. typedef filesystem_traits<C> traits_type;
  119. /// \brief The current parameterisation of the type
  120. typedef path_compare<C> class_type;
  121. public:
  122. /// \brief Function call, compares \c s1 with \c s2
  123. ///
  124. /// \note The comparison is determined by evaluation the full-paths of both \c s1 and \c s2
  125. #ifdef STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT
  126. template <ss_typename_param_k T1, ss_typename_param_k T2>
  127. result_type operator ()(T1 const& s1, T2 const& s2)
  128. #else /* ? STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT */
  129. result_type operator ()(first_argument_type s1, second_argument_type s2)
  130. #endif /* STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT */
  131. {
  132. return compare_(stlsoft_ns_qual(c_str_ptr)(s1), stlsoft_ns_qual(c_str_ptr)(s2));
  133. }
  134. // Implementation
  135. private:
  136. result_type compare_(char_type const* s1, char_type const* s2)
  137. {
  138. basic_file_path_buffer<char_type> path1;
  139. basic_file_path_buffer<char_type> path2;
  140. if( !traits_type::get_full_path_name(s1, path1.size(), &path1[0]) ||
  141. !traits_type::get_full_path_name(s2, path2.size(), &path2[0]))
  142. {
  143. return false;
  144. }
  145. else
  146. {
  147. traits_type::remove_dir_end(&path1[0]);
  148. traits_type::remove_dir_end(&path2[0]);
  149. s1 = path1.c_str();
  150. s2 = path2.c_str();
  151. return 0 == traits_type::str_compare(s1, s2);
  152. }
  153. }
  154. };
  155. /** \brief Predicate that indicates whether a given path exists
  156. *
  157. * \ingroup group__library__filesystem
  158. *
  159. * \note Does not expand environment variables in the argument passed to
  160. * the function call operator
  161. *
  162. * \param C The character type
  163. * \param A The argument type; defaults to C const*
  164. */
  165. template< ss_typename_param_k C
  166. , ss_typename_param_k A = C const*
  167. >
  168. // [[synesis:class:function-class:unary-predicate: path_exists<T<C>, T<A>>]]
  169. struct path_exists
  170. : public unixstl_ns_qual_std(unary_function)<A, us_bool_t>
  171. {
  172. private:
  173. typedef unixstl_ns_qual_std(unary_function)<A, us_bool_t> parent_class_type;
  174. typedef filesystem_traits<C> traits_type;
  175. public:
  176. /// \brief The character type
  177. typedef C char_type;
  178. /// \brief The argument type
  179. typedef A argument_type;
  180. /// \brief The current parameterisation of the type
  181. typedef path_exists<C, A> class_type;
  182. public:
  183. #ifdef STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT
  184. template <ss_typename_param_k S>
  185. us_bool_t operator ()(S const& s) const
  186. #else /* ? STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT */
  187. us_bool_t operator ()(argument_type s) const
  188. #endif /* STLSOFT_CF_MEMBER_TEMPLATE_FUNCTION_SUPPORT */
  189. {
  190. return traits_type::file_exists(stlsoft_ns_qual(c_str_ptr)(s));
  191. }
  192. };
  193. ////////////////////////////////////////////////////////////////////////////
  194. // Unit-testing
  195. #ifdef STLSOFT_UNITTEST
  196. # include "./unittest/functionals_unittest_.h"
  197. #endif /* STLSOFT_UNITTEST */
  198. /* ////////////////////////////////////////////////////////////////////// */
  199. #ifndef _UNIXSTL_NO_NAMESPACE
  200. # if defined(_STLSOFT_NO_NAMESPACE) || \
  201. defined(STLSOFT_DOCUMENTATION_SKIP_SECTION)
  202. } // namespace unixstl
  203. # else
  204. } // namespace unixstl_project
  205. } // namespace stlsoft
  206. # endif /* _STLSOFT_NO_NAMESPACE */
  207. #endif /* !_UNIXSTL_NO_NAMESPACE */
  208. /* ////////////////////////////////////////////////////////////////////// */
  209. #endif /* UNIXSTL_INCL_UNIXSTL_FILESYSTEM_HPP_FILESYSTEM_FUNCTIONALS */
  210. /* ///////////////////////////// end of file //////////////////////////// */