File indexing completed on 2025-01-18 09:53:52
0001
0002
0003
0004
0005
0006
0007
0008 #ifndef BOOST_XPRESSIVE_DETAIL_UTILITY_ALGORITHM_HPP_EAN_10_04_2005
0009 #define BOOST_XPRESSIVE_DETAIL_UTILITY_ALGORITHM_HPP_EAN_10_04_2005
0010
0011
0012 #if defined(_MSC_VER)
0013 # pragma once
0014 #endif
0015
0016 #include <string>
0017 #include <climits>
0018 #include <algorithm>
0019 #include <boost/version.hpp>
0020 #include <boost/range/end.hpp>
0021 #include <boost/range/begin.hpp>
0022 #include <boost/range/size.hpp>
0023 #include <boost/range/value_type.hpp>
0024 #include <boost/type_traits/remove_const.hpp>
0025 #include <boost/iterator/iterator_traits.hpp>
0026 #include <boost/xpressive/detail/utility/ignore_unused.hpp>
0027
0028 namespace boost { namespace xpressive { namespace detail
0029 {
0030
0031
0032
0033
0034 template<typename InIter, typename Pred>
0035 inline bool any(InIter begin, InIter end, Pred pred)
0036 {
0037 return end != std::find_if(begin, end, pred);
0038 }
0039
0040
0041
0042
0043 template<typename FwdIter, typename Diff, typename Pred>
0044 FwdIter find_nth_if(FwdIter begin, FwdIter end, Diff count, Pred pred)
0045 {
0046 for(; begin != end; ++begin)
0047 {
0048 if(pred(*begin) && 0 == count--)
0049 {
0050 return begin;
0051 }
0052 }
0053
0054 return end;
0055 }
0056
0057
0058
0059
0060 template<typename InIter, typename Traits>
0061 int toi(InIter &begin, InIter end, Traits const &tr, int radix = 10, int max = INT_MAX)
0062 {
0063 detail::ignore_unused(tr);
0064 int i = 0, c = 0;
0065 for(; begin != end && -1 != (c = tr.value(*begin, radix)); ++begin)
0066 {
0067 if(max < ((i *= radix) += c))
0068 return i / radix;
0069 }
0070 return i;
0071 }
0072
0073
0074
0075
0076 template<typename BidiIter, typename Diff>
0077 inline bool advance_to_impl(BidiIter & iter, Diff diff, BidiIter end, std::bidirectional_iterator_tag)
0078 {
0079 for(; 0 < diff && iter != end; --diff)
0080 ++iter;
0081 for(; 0 > diff && iter != end; ++diff)
0082 --iter;
0083 return 0 == diff;
0084 }
0085
0086 template<typename RandIter, typename Diff>
0087 inline bool advance_to_impl(RandIter & iter, Diff diff, RandIter end, std::random_access_iterator_tag)
0088 {
0089 if(0 < diff)
0090 {
0091 if((end - iter) < diff)
0092 return false;
0093 }
0094 else if(0 > diff)
0095 {
0096 if((iter - end) < -diff)
0097 return false;
0098 }
0099 iter += diff;
0100 return true;
0101 }
0102
0103 template<typename Iter, typename Diff>
0104 inline bool advance_to(Iter & iter, Diff diff, Iter end)
0105 {
0106 return detail::advance_to_impl(iter, diff, end, typename iterator_category<Iter>::type());
0107 }
0108
0109
0110
0111
0112 template<typename T>
0113 struct range_data
0114 : range_value<T>
0115 {};
0116
0117 template<typename T>
0118 struct range_data<T *>
0119 : remove_const<T>
0120 {};
0121
0122 template<typename T> std::ptrdiff_t is_null_terminated(T const &) { return 0; }
0123 #if BOOST_VERSION >= 103500
0124 inline std::ptrdiff_t is_null_terminated(char const *) { return 1; }
0125 #ifndef BOOST_XPRESSIVE_NO_WREGEX
0126 inline std::ptrdiff_t is_null_terminated(wchar_t const *) { return 1; }
0127 #endif
0128 #endif
0129
0130
0131
0132
0133 template<typename Cont>
0134 typename range_data<Cont>::type const *data_begin(Cont const &cont)
0135 {
0136 return &*boost::begin(cont);
0137 }
0138
0139 template<typename Cont>
0140 typename range_data<Cont>::type const *data_end(Cont const &cont)
0141 {
0142 return &*boost::begin(cont) + boost::size(cont) - is_null_terminated(cont);
0143 }
0144
0145 template<typename Char, typename Traits, typename Alloc>
0146 Char const *data_begin(std::basic_string<Char, Traits, Alloc> const &str)
0147 {
0148 return str.data();
0149 }
0150
0151 template<typename Char, typename Traits, typename Alloc>
0152 Char const *data_end(std::basic_string<Char, Traits, Alloc> const &str)
0153 {
0154 return str.data() + str.size();
0155 }
0156
0157 template<typename Char>
0158 Char const *data_begin(Char const *const &sz)
0159 {
0160 return sz;
0161 }
0162
0163 template<typename Char>
0164 Char const *data_end(Char const *const &sz)
0165 {
0166 Char const *tmp = sz;
0167 for(; *tmp; ++tmp)
0168 ;
0169 return tmp;
0170 }
0171
0172 }}}
0173
0174 #endif