forked from boostorg/static_string
Fix InputIterator overloads
This commit is contained in:
@ -31,13 +31,6 @@ using static_string = basic_static_string<N, char, std::char_traits<char>>;
|
|||||||
template<std::size_t N>
|
template<std::size_t N>
|
||||||
using static_wstring = basic_static_string<N, wchar_t, std::char_traits<wchar_t>>;
|
using static_wstring = basic_static_string<N, wchar_t, std::char_traits<wchar_t>>;
|
||||||
|
|
||||||
// At minimum an integral type shall not qualify as an iterator (Agustin Berge)
|
|
||||||
// Applicable standardese: http://eel.is/c++draft/containers#container.requirements.general-17
|
|
||||||
template<class T>
|
|
||||||
using is_input_iterator =
|
|
||||||
std::integral_constant<bool,
|
|
||||||
! std::is_integral<T>::value>;
|
|
||||||
|
|
||||||
// Find the smallest width integral type that can hold a value as large as N (Glen Fernandes)
|
// Find the smallest width integral type that can hold a value as large as N (Glen Fernandes)
|
||||||
template<std::size_t N>
|
template<std::size_t N>
|
||||||
using smallest_width =
|
using smallest_width =
|
||||||
@ -74,15 +67,51 @@ struct is_nothrow_convertible<From, To, typename std::enable_if<
|
|||||||
template<typename...>
|
template<typename...>
|
||||||
using void_t = void;
|
using void_t = void;
|
||||||
|
|
||||||
// Check if iterator can do subtraction, meaning its random access
|
// Simplified check for if a type is an iterator
|
||||||
|
template<class T, typename = void>
|
||||||
|
struct is_iterator : std::false_type { };
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
struct is_iterator<T,
|
||||||
|
void_t<typename T::difference_type,
|
||||||
|
typename T::value_type,
|
||||||
|
typename T::pointer,
|
||||||
|
typename T::reference,
|
||||||
|
typename T::iterator_category>>
|
||||||
|
: std::true_type { };
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
struct is_iterator<T*, void>
|
||||||
|
: std::true_type { };
|
||||||
|
|
||||||
|
template<class T, typename = void>
|
||||||
|
struct is_input_iterator : std::false_type { };
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
struct is_input_iterator<T, typename std::enable_if<is_iterator<T>::value &&
|
||||||
|
std::is_convertible<typename std::iterator_traits<T>::iterator_category,
|
||||||
|
std::input_iterator_tag>::value>::type>
|
||||||
|
: std::true_type { };
|
||||||
|
|
||||||
|
template<class T, typename = void>
|
||||||
|
struct is_forward_iterator : std::false_type { };
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
struct is_forward_iterator<T, typename std::enable_if<is_iterator<T>::value &&
|
||||||
|
std::is_convertible<typename std::iterator_traits<T>::iterator_category,
|
||||||
|
std::forward_iterator_tag>::value>::type>
|
||||||
|
: std::true_type { };
|
||||||
|
|
||||||
template<typename T, typename = void>
|
template<typename T, typename = void>
|
||||||
struct is_difference_iter : std::false_type { };
|
struct is_subtractable
|
||||||
|
: std::false_type { };
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
struct is_difference_iter<T, void_t<decltype(std::declval<T>() - std::declval<T>())>> : std::true_type { };
|
struct is_subtractable<T, void_t<decltype(std::declval<T&>() - std::declval<T&>())>>
|
||||||
|
: std::true_type { };
|
||||||
|
|
||||||
// constexpr distance for c++14
|
// constexpr distance for c++14
|
||||||
template<typename InputIt, typename std::enable_if<!is_difference_iter<InputIt>::value>::type* = nullptr>
|
template<typename InputIt, typename std::enable_if<!is_subtractable<InputIt>::value>::type* = nullptr>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
typename std::iterator_traits<InputIt>::difference_type
|
typename std::iterator_traits<InputIt>::difference_type
|
||||||
distance(InputIt first, InputIt last)
|
distance(InputIt first, InputIt last)
|
||||||
@ -92,7 +121,7 @@ distance(InputIt first, InputIt last)
|
|||||||
return dist;
|
return dist;
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename RandomIt, typename std::enable_if<is_difference_iter<RandomIt>::value>::type* = nullptr>
|
template<typename RandomIt, typename std::enable_if<is_subtractable<RandomIt>::value>::type* = nullptr>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
typename std::iterator_traits<RandomIt>::difference_type
|
typename std::iterator_traits<RandomIt>::difference_type
|
||||||
distance(RandomIt first, RandomIt last)
|
distance(RandomIt first, RandomIt last)
|
||||||
|
@ -224,12 +224,17 @@ assign(
|
|||||||
detail::is_input_iterator<InputIterator>::value,
|
detail::is_input_iterator<InputIterator>::value,
|
||||||
basic_static_string&>::type
|
basic_static_string&>::type
|
||||||
{
|
{
|
||||||
std::size_t const n = detail::distance(first, last);
|
auto ptr = data();
|
||||||
BOOST_STATIC_STRING_THROW_IF(n > max_size(),
|
for (std::size_t i = 0; first != last; ++first, ++ptr, ++i)
|
||||||
std::length_error{"n > max_size()"});
|
{
|
||||||
this->set_size(n);
|
if (1 > max_size() - i)
|
||||||
for(auto it = data(); first != last; ++it, ++first)
|
{
|
||||||
Traits::assign(*it, *first);
|
this->set_size(i);
|
||||||
|
BOOST_STATIC_STRING_THROW(std::length_error{"n > max_size()"});
|
||||||
|
}
|
||||||
|
Traits::assign(*ptr, *first);
|
||||||
|
}
|
||||||
|
this->set_size(ptr - data());
|
||||||
term();
|
term();
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@ -362,22 +367,22 @@ insert(
|
|||||||
}
|
}
|
||||||
|
|
||||||
template<std::size_t N, typename CharT, typename Traits>
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
template<class InputIterator>
|
template<class ForwardIterator>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
auto
|
auto
|
||||||
basic_static_string<N, CharT, Traits>::
|
basic_static_string<N, CharT, Traits>::
|
||||||
insert(
|
insert(
|
||||||
const_iterator pos,
|
const_iterator pos,
|
||||||
InputIterator first,
|
ForwardIterator first,
|
||||||
InputIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
ForwardIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
||||||
typename std::enable_if<
|
typename std::enable_if<
|
||||||
detail::is_input_iterator<
|
detail::is_forward_iterator<
|
||||||
InputIterator>::value, iterator>::type
|
ForwardIterator>::value, iterator>::type
|
||||||
{
|
{
|
||||||
const auto curr_size = size();
|
const auto curr_size = size();
|
||||||
const auto curr_data = data();
|
const auto curr_data = data();
|
||||||
const auto count = detail::distance(first, last);
|
const auto count = detail::distance(first, last);
|
||||||
const auto index = pos - begin();
|
const auto index = pos - curr_data;
|
||||||
const auto s = &*first;
|
const auto s = &*first;
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
index > curr_size, std::out_of_range{"index > size()"});
|
index > curr_size, std::out_of_range{"index > size()"});
|
||||||
@ -408,6 +413,33 @@ insert(
|
|||||||
return begin() + index;
|
return begin() + index;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
|
template<class InputIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
auto
|
||||||
|
basic_static_string<N, CharT, Traits>::
|
||||||
|
insert(
|
||||||
|
const_iterator pos,
|
||||||
|
InputIterator first,
|
||||||
|
InputIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
||||||
|
typename std::enable_if<
|
||||||
|
detail::is_input_iterator<
|
||||||
|
InputIterator>::value &&
|
||||||
|
! detail::is_forward_iterator<
|
||||||
|
InputIterator>::value, iterator>::type
|
||||||
|
{
|
||||||
|
const auto curr_size = size();
|
||||||
|
const auto curr_data = data();
|
||||||
|
const auto count = read_back(first, last);
|
||||||
|
const auto index = pos - curr_data;
|
||||||
|
const auto s = curr_data + curr_size + 1;
|
||||||
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
|
index > curr_size, std::out_of_range{"index > size()"});
|
||||||
|
std::rotate(&curr_data[index], &curr_data[curr_size + 1], &curr_data[curr_size + count + 1]);
|
||||||
|
this->set_size(curr_size + count);
|
||||||
|
return curr_data + index;
|
||||||
|
}
|
||||||
|
|
||||||
template<std::size_t N, typename CharT, typename Traits>
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
auto
|
auto
|
||||||
@ -419,7 +451,7 @@ insert(
|
|||||||
{
|
{
|
||||||
const auto curr_size = size();
|
const auto curr_size = size();
|
||||||
const auto curr_data = data();
|
const auto curr_data = data();
|
||||||
const auto index = pos - begin();
|
const auto index = pos - curr_data;
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
index > curr_size, std::out_of_range{"index > size()"});
|
index > curr_size, std::out_of_range{"index > size()"});
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
@ -691,24 +723,24 @@ replace(
|
|||||||
}
|
}
|
||||||
|
|
||||||
template<std::size_t N, typename CharT, typename Traits>
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
template<typename InputIterator>
|
template<typename ForwardIterator>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
auto
|
auto
|
||||||
basic_static_string<N, CharT, Traits>::
|
basic_static_string<N, CharT, Traits>::
|
||||||
replace(
|
replace(
|
||||||
const_iterator i1,
|
const_iterator i1,
|
||||||
const_iterator i2,
|
const_iterator i2,
|
||||||
InputIterator j1,
|
ForwardIterator j1,
|
||||||
InputIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
ForwardIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
||||||
typename std::enable_if<
|
typename std::enable_if<
|
||||||
detail::is_input_iterator<InputIterator>::value,
|
detail::is_forward_iterator<ForwardIterator>::value,
|
||||||
basic_static_string<N, CharT, Traits>&>::type
|
basic_static_string<N, CharT, Traits>&>::type
|
||||||
{
|
{
|
||||||
const auto curr_size = size();
|
const auto curr_size = size();
|
||||||
const auto curr_data = data();
|
const auto curr_data = data();
|
||||||
std::size_t n1 = std::distance(i1, i2);
|
std::size_t n1 = detail::distance(i1, i2);
|
||||||
const std::size_t n2 = detail::distance(j1, j2);
|
const std::size_t n2 = detail::distance(j1, j2);
|
||||||
const std::size_t pos = i1 - begin();
|
const std::size_t pos = i1 - curr_data;
|
||||||
const auto s = &*j1;
|
const auto s = &*j1;
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
pos > curr_size, std::out_of_range{"pos > size()"});
|
pos > curr_size, std::out_of_range{"pos > size()"});
|
||||||
@ -754,6 +786,44 @@ replace(
|
|||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
|
template<typename InputIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
auto
|
||||||
|
basic_static_string<N, CharT, Traits>::
|
||||||
|
replace(
|
||||||
|
const_iterator i1,
|
||||||
|
const_iterator i2,
|
||||||
|
InputIterator j1,
|
||||||
|
InputIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
||||||
|
typename std::enable_if<
|
||||||
|
detail::is_input_iterator<
|
||||||
|
InputIterator>::value &&
|
||||||
|
! detail::is_forward_iterator<
|
||||||
|
InputIterator>::value,
|
||||||
|
basic_static_string<N, CharT, Traits>&>::type
|
||||||
|
{
|
||||||
|
const auto curr_size = size();
|
||||||
|
const auto curr_data = data();
|
||||||
|
std::size_t n1 = detail::distance(i1, i2);
|
||||||
|
const std::size_t n2 = read_back(j1, j2);
|
||||||
|
const std::size_t pos = i1 - curr_data;
|
||||||
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
|
pos > curr_size, std::out_of_range{"pos > size()"});
|
||||||
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
|
curr_size - (std::min)(n1, curr_size - pos) >= max_size() - n2,
|
||||||
|
std::length_error{"replaced string exceeds max_size()"});
|
||||||
|
// Rotate to the correct order. [i2, end] will now start with the replaced string, continue to the existing string not being replaced, and end with a null terminator
|
||||||
|
std::rotate(&curr_data[pos], &curr_data[curr_size + 1], &curr_data[curr_size + n2 + 1]);
|
||||||
|
// Cap the size
|
||||||
|
if (pos + n1 >= curr_size)
|
||||||
|
n1 = curr_size - pos;
|
||||||
|
// Move everything from the end of the splice point to the end of the rotated string to the begining of the splice point
|
||||||
|
Traits::move(&curr_data[pos + n2], &curr_data[pos + n2 + n1], (curr_size + (n2 - n1)) - pos);
|
||||||
|
this->set_size(curr_size + (n2 - n1));
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
template<std::size_t N, typename CharT, typename Traits>
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
auto
|
auto
|
||||||
@ -767,7 +837,7 @@ replace(
|
|||||||
const auto curr_size = size();
|
const auto curr_size = size();
|
||||||
const auto curr_data = data();
|
const auto curr_data = data();
|
||||||
std::size_t n1 = detail::distance(i1, i2);
|
std::size_t n1 = detail::distance(i1, i2);
|
||||||
const std::size_t pos = i1 - begin();
|
const std::size_t pos = i1 - curr_data;
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
pos > curr_size, std::out_of_range{"pos > size()"});
|
pos > curr_size, std::out_of_range{"pos > size()"});
|
||||||
BOOST_STATIC_STRING_THROW_IF(
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
@ -923,6 +993,27 @@ assign_char(CharT, std::false_type) BOOST_STATIC_STRING_COND_NOEXCEPT ->
|
|||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<std::size_t N, typename CharT, typename Traits>
|
||||||
|
template<typename InputIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
auto
|
||||||
|
basic_static_string<N, CharT, Traits>::
|
||||||
|
read_back(
|
||||||
|
InputIterator first,
|
||||||
|
InputIterator last) ->
|
||||||
|
std::size_t
|
||||||
|
{
|
||||||
|
const auto curr_data = data();
|
||||||
|
auto new_size = size();
|
||||||
|
for (; first != last; ++first)
|
||||||
|
{
|
||||||
|
BOOST_STATIC_STRING_THROW_IF(
|
||||||
|
1 > max_size() - new_size, std::length_error{"count > max_size() - size()"});
|
||||||
|
Traits::assign(curr_data[++new_size], *first);
|
||||||
|
}
|
||||||
|
return new_size - size();
|
||||||
|
}
|
||||||
|
|
||||||
// string
|
// string
|
||||||
|
|
||||||
static_string<std::numeric_limits<int>::digits10 + 1>
|
static_string<std::numeric_limits<int>::digits10 + 1>
|
||||||
|
@ -936,14 +936,42 @@ public:
|
|||||||
iterator
|
iterator
|
||||||
#else
|
#else
|
||||||
typename std::enable_if<
|
typename std::enable_if<
|
||||||
detail::is_input_iterator<InputIterator>::value,
|
detail::is_input_iterator<
|
||||||
iterator>::type
|
InputIterator>::value &&
|
||||||
|
! detail::is_forward_iterator<
|
||||||
|
InputIterator>::value, iterator>::type
|
||||||
#endif
|
#endif
|
||||||
insert(
|
insert(
|
||||||
const_iterator pos,
|
const_iterator pos,
|
||||||
InputIterator first,
|
InputIterator first,
|
||||||
InputIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
InputIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
|
/** Insert into the string.
|
||||||
|
|
||||||
|
Inserts characters from the range `(first, last)` before the element (if any) pointed by `pos`
|
||||||
|
|
||||||
|
The inserted string can contain null characters.
|
||||||
|
This function does not participate in overload resolution if
|
||||||
|
`LegacyForwardIterator` does not satisfy <em>LegacyForwardIterator</em>
|
||||||
|
|
||||||
|
@throw std::length_error if `std::distance(first, last) > max_size() - size()`
|
||||||
|
@return An iterator to the first inserted character or pos if no insertion took place
|
||||||
|
*/
|
||||||
|
template<typename ForwardIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
#if GENERATING_DOCUMENTATION
|
||||||
|
iterator
|
||||||
|
#else
|
||||||
|
typename std::enable_if<
|
||||||
|
detail::is_forward_iterator<
|
||||||
|
ForwardIterator>::value,
|
||||||
|
iterator>::type
|
||||||
|
#endif
|
||||||
|
insert(
|
||||||
|
const_iterator pos,
|
||||||
|
ForwardIterator first,
|
||||||
|
ForwardIterator last) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
/** Insert into the string.
|
/** Insert into the string.
|
||||||
|
|
||||||
Inserts elements from initializer list `ilist` before the element (if any) pointed by `pos`
|
Inserts elements from initializer list `ilist` before the element (if any) pointed by `pos`
|
||||||
@ -954,8 +982,8 @@ public:
|
|||||||
@return An iterator to the first inserted character or pos if no insertion took place
|
@return An iterator to the first inserted character or pos if no insertion took place
|
||||||
*/
|
*/
|
||||||
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
iterator
|
iterator
|
||||||
insert(
|
insert(
|
||||||
const_iterator pos,
|
const_iterator pos,
|
||||||
std::initializer_list<CharT> ilist) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
std::initializer_list<CharT> ilist) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
@ -1856,8 +1884,11 @@ public:
|
|||||||
basic_static_string&
|
basic_static_string&
|
||||||
#else
|
#else
|
||||||
typename std::enable_if<
|
typename std::enable_if<
|
||||||
detail::is_input_iterator<InputIterator>::value,
|
detail::is_input_iterator<
|
||||||
basic_static_string&>::type
|
InputIterator>::value &&
|
||||||
|
! detail::is_forward_iterator<
|
||||||
|
InputIterator>::value,
|
||||||
|
basic_static_string<N, CharT, Traits>&>::type
|
||||||
#endif
|
#endif
|
||||||
replace(
|
replace(
|
||||||
const_iterator i1,
|
const_iterator i1,
|
||||||
@ -1865,6 +1896,30 @@ public:
|
|||||||
InputIterator j1,
|
InputIterator j1,
|
||||||
InputIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
InputIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
|
/** Replace a subset of the string.
|
||||||
|
|
||||||
|
Replaces the part of the string indicated by `[i1, i2)` with the characters in the range `[j1, j2)`.
|
||||||
|
|
||||||
|
@throw std::out_of_range if `i1` and `i2` do not refer to elements within the range `[0, size())`
|
||||||
|
@throw std::length_error if the resulting string exceeds `max_size()`
|
||||||
|
@return `*this`
|
||||||
|
*/
|
||||||
|
template<typename ForwardIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
#if GENERATING_DOCUMENTATION
|
||||||
|
basic_static_string&
|
||||||
|
#else
|
||||||
|
typename std::enable_if<
|
||||||
|
detail::is_forward_iterator<
|
||||||
|
ForwardIterator>::value,
|
||||||
|
basic_static_string<N, CharT, Traits>&>::type
|
||||||
|
#endif
|
||||||
|
replace(
|
||||||
|
const_iterator i1,
|
||||||
|
const_iterator i2,
|
||||||
|
ForwardIterator j1,
|
||||||
|
ForwardIterator j2) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
/** Replace a subset of the string.
|
/** Replace a subset of the string.
|
||||||
|
|
||||||
Replaces the part of the string indicated by `[i1, i2)` with the characters in the initializer list `il`.
|
Replaces the part of the string indicated by `[i1, i2)` with the characters in the initializer list `il`.
|
||||||
@ -2427,6 +2482,14 @@ private:
|
|||||||
|
|
||||||
basic_static_string&
|
basic_static_string&
|
||||||
assign_char(CharT ch, std::false_type) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
assign_char(CharT ch, std::false_type) BOOST_STATIC_STRING_COND_NOEXCEPT;
|
||||||
|
|
||||||
|
// Returns the size of data read from input iterator. Read data begins at data() + size() + 1.
|
||||||
|
template<typename InputIterator>
|
||||||
|
BOOST_STATIC_STRING_CPP14_CONSTEXPR
|
||||||
|
std::size_t
|
||||||
|
read_back(
|
||||||
|
InputIterator first,
|
||||||
|
InputIterator last);
|
||||||
};
|
};
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
|
Reference in New Issue
Block a user