// Bits and pieces used in algorithms -*- C++ -*-
-// Copyright (C) 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
+// Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007
+// Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library. This library is free
// software; you can redistribute it and/or modify it under the
#include <bits/c++config.h>
#include <cstring>
+#include <cwchar>
#include <climits>
#include <cstdlib>
#include <cstddef>
#include <iosfwd>
#include <bits/stl_pair.h>
#include <bits/cpp_type_traits.h>
+#include <ext/type_traits.h>
#include <bits/stl_iterator_base_types.h>
#include <bits/stl_iterator_base_funcs.h>
#include <bits/stl_iterator.h>
#include <bits/concept_check.h>
#include <debug/debug.h>
-namespace std
-{
+_GLIBCXX_BEGIN_NAMESPACE(std)
/**
* @brief Swaps two values.
iter_swap(__a, __b);
}
- #undef min
- #undef max
-
/**
* @brief This does what you think it does.
* @param a A thing of arbitrary type.
return std::__copy<__simple, _Category>::copy(__first, __last, __result);
}
+ // Helpers for streambuf iterators (either istream or ostream).
+ template<typename _CharT>
+ typename __gnu_cxx::__enable_if<__is_char<_CharT>::__value,
+ ostreambuf_iterator<_CharT> >::__type
+ __copy_aux(_CharT*, _CharT*, ostreambuf_iterator<_CharT>);
+
+ template<typename _CharT>
+ typename __gnu_cxx::__enable_if<__is_char<_CharT>::__value,
+ ostreambuf_iterator<_CharT> >::__type
+ __copy_aux(const _CharT*, const _CharT*, ostreambuf_iterator<_CharT>);
+
+ template<typename _CharT>
+ typename __gnu_cxx::__enable_if<__is_char<_CharT>::__value, _CharT*>::__type
+ __copy_aux(istreambuf_iterator<_CharT>, istreambuf_iterator<_CharT>,
+ _CharT*);
+
template<bool, bool>
struct __copy_normal
{
template<typename _II, typename _OI>
static _OI
- copy_n(_II __first, _II __last, _OI __result)
+ __copy_n(_II __first, _II __last, _OI __result)
{ return std::__copy_aux(__first, __last, __result); }
};
{
template<typename _II, typename _OI>
static _OI
- copy_n(_II __first, _II __last, _OI __result)
+ __copy_n(_II __first, _II __last, _OI __result)
{ return std::__copy_aux(__first.base(), __last.base(), __result); }
};
{
template<typename _II, typename _OI>
static _OI
- copy_n(_II __first, _II __last, _OI __result)
+ __copy_n(_II __first, _II __last, _OI __result)
{ return _OI(std::__copy_aux(__first, __last, __result.base())); }
};
{
template<typename _II, typename _OI>
static _OI
- copy_n(_II __first, _II __last, _OI __result)
+ __copy_n(_II __first, _II __last, _OI __result)
{ return _OI(std::__copy_aux(__first.base(), __last.base(),
__result.base())); }
};
const bool __in = __is_normal_iterator<_InputIterator>::__value;
const bool __out = __is_normal_iterator<_OutputIterator>::__value;
- return std::__copy_normal<__in, __out>::copy_n(__first, __last,
- __result);
+ return std::__copy_normal<__in, __out>::__copy_n(__first, __last,
+ __result);
}
-
+
+ // Overload for streambuf iterators.
+ template<typename _CharT>
+ typename __gnu_cxx::__enable_if<__is_char<_CharT>::__value,
+ ostreambuf_iterator<_CharT> >::__type
+ copy(istreambuf_iterator<_CharT>, istreambuf_iterator<_CharT>,
+ ostreambuf_iterator<_CharT>);
+
template<bool, typename>
struct __copy_backward
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
{
while (__first != __last)
*--__result = *--__last;
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
{
typename iterator_traits<_BI1>::difference_type __n;
for (__n = __last - __first; __n > 0; --__n)
{
template<typename _Tp>
static _Tp*
- copy_b(const _Tp* __first, const _Tp* __last, _Tp* __result)
+ __copy_b(const _Tp* __first, const _Tp* __last, _Tp* __result)
{
const ptrdiff_t _Num = __last - __first;
std::memmove(__result - _Num, __first, sizeof(_Tp) * _Num);
&& __is_pointer<_BI2>::__value
&& __are_same<_ValueType1, _ValueType2>::__value);
- return std::__copy_backward<__simple, _Category>::copy_b(__first, __last,
- __result);
+ return std::__copy_backward<__simple, _Category>::__copy_b(__first,
+ __last,
+ __result);
}
template<bool, bool>
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
{ return std::__copy_backward_aux(__first, __last, __result); }
};
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
{ return std::__copy_backward_aux(__first.base(), __last.base(),
__result); }
};
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
{ return _BI2(std::__copy_backward_aux(__first, __last,
__result.base())); }
};
{
template<typename _BI1, typename _BI2>
static _BI2
- copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
+ __copy_b_n(_BI1 __first, _BI1 __last, _BI2 __result)
{ return _BI2(std::__copy_backward_aux(__first.base(), __last.base(),
__result.base())); }
};
const bool __bi1 = __is_normal_iterator<_BI1>::__value;
const bool __bi2 = __is_normal_iterator<_BI2>::__value;
- return std::__copy_backward_normal<__bi1, __bi2>::copy_b_n(__first, __last,
- __result);
+ return std::__copy_backward_normal<__bi1, __bi2>::__copy_b_n(__first,
+ __last,
+ __result);
}
+
template<bool>
struct __fill
{
}
};
- /**
- * @brief Fills the range [first,last) with copies of value.
- * @param first A forward iterator.
- * @param last A forward iterator.
- * @param value A reference-to-const of arbitrary type.
- * @return Nothing.
- *
- * This function fills a range with copies of the same value. For one-byte
- * types filling contiguous areas of memory, this becomes an inline call to
- * @c memset.
- */
template<typename _ForwardIterator, typename _Tp>
- void
- fill(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value)
+ inline void
+ __fill_aux(_ForwardIterator __first, _ForwardIterator __last,
+ const _Tp& __value)
{
- // concept requirements
- __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
- _ForwardIterator>)
- __glibcxx_requires_valid_range(__first, __last);
-
const bool __scalar = __is_scalar<_Tp>::__value;
std::__fill<__scalar>::fill(__first, __last, __value);
}
- // Specialization: for one-byte types we can use memset.
+ // Specialization: for char types we can use memset (wmemset).
inline void
- fill(unsigned char* __first, unsigned char* __last, const unsigned char& __c)
+ __fill_aux(unsigned char* __first, unsigned char* __last,
+ const unsigned char& __c)
{
- __glibcxx_requires_valid_range(__first, __last);
const unsigned char __tmp = __c;
std::memset(__first, __tmp, __last - __first);
}
inline void
- fill(signed char* __first, signed char* __last, const signed char& __c)
+ __fill_aux(signed char* __first, signed char* __last,
+ const signed char& __c)
{
- __glibcxx_requires_valid_range(__first, __last);
const signed char __tmp = __c;
std::memset(__first, static_cast<unsigned char>(__tmp), __last - __first);
}
inline void
- fill(char* __first, char* __last, const char& __c)
+ __fill_aux(char* __first, char* __last, const char& __c)
{
- __glibcxx_requires_valid_range(__first, __last);
const char __tmp = __c;
std::memset(__first, static_cast<unsigned char>(__tmp), __last - __first);
}
+#ifdef _GLIBCXX_USE_WCHAR_T
+ inline void
+ __fill_aux(wchar_t* __first, wchar_t* __last, const wchar_t& __c)
+ {
+ const wchar_t __tmp = __c;
+ std::wmemset(__first, __tmp, __last - __first);
+ }
+#endif
+
+ template<bool>
+ struct __fill_normal
+ {
+ template<typename _ForwardIterator, typename _Tp>
+ static void
+ __fill_n(_ForwardIterator __first, _ForwardIterator __last,
+ const _Tp& __value)
+ { std::__fill_aux(__first, __last, __value); }
+ };
+
+ template<>
+ struct __fill_normal<true>
+ {
+ template<typename _ForwardIterator, typename _Tp>
+ static void
+ __fill_n(_ForwardIterator __first, _ForwardIterator __last,
+ const _Tp& __value)
+ { std::__fill_aux(__first.base(), __last.base(), __value); }
+ };
+
+ /**
+ * @brief Fills the range [first,last) with copies of value.
+ * @param first A forward iterator.
+ * @param last A forward iterator.
+ * @param value A reference-to-const of arbitrary type.
+ * @return Nothing.
+ *
+ * This function fills a range with copies of the same value. For char
+ * types filling contiguous areas of memory, this becomes an inline call
+ * to @c memset or @c wmemset.
+ */
+ template<typename _ForwardIterator, typename _Tp>
+ inline void
+ fill(_ForwardIterator __first, _ForwardIterator __last, const _Tp& __value)
+ {
+ // concept requirements
+ __glibcxx_function_requires(_Mutable_ForwardIteratorConcept<
+ _ForwardIterator>)
+ __glibcxx_requires_valid_range(__first, __last);
+
+ const bool __fi = __is_normal_iterator<_ForwardIterator>::__value;
+ std::__fill_normal<__fi>::__fill_n(__first, __last, __value);
+ }
+
+
template<bool>
struct __fill_n
{
}
};
- /**
- * @brief Fills the range [first,first+n) with copies of value.
- * @param first An output iterator.
- * @param n The count of copies to perform.
- * @param value A reference-to-const of arbitrary type.
- * @return The iterator at first+n.
- *
- * This function fills a range with copies of the same value. For one-byte
- * types filling contiguous areas of memory, this becomes an inline call to
- * @c memset.
- */
template<typename _OutputIterator, typename _Size, typename _Tp>
- _OutputIterator
- fill_n(_OutputIterator __first, _Size __n, const _Tp& __value)
+ inline _OutputIterator
+ __fill_n_aux(_OutputIterator __first, _Size __n, const _Tp& __value)
{
- // concept requirements
- __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator, _Tp>)
-
const bool __scalar = __is_scalar<_Tp>::__value;
return std::__fill_n<__scalar>::fill_n(__first, __n, __value);
}
template<typename _Size>
inline unsigned char*
- fill_n(unsigned char* __first, _Size __n, const unsigned char& __c)
+ __fill_n_aux(unsigned char* __first, _Size __n, const unsigned char& __c)
{
- std::fill(__first, __first + __n, __c);
+ std::__fill_aux(__first, __first + __n, __c);
return __first + __n;
}
template<typename _Size>
inline signed char*
- fill_n(char* __first, _Size __n, const signed char& __c)
+ __fill_n_aux(signed char* __first, _Size __n, const signed char& __c)
{
- std::fill(__first, __first + __n, __c);
+ std::__fill_aux(__first, __first + __n, __c);
return __first + __n;
}
template<typename _Size>
inline char*
- fill_n(char* __first, _Size __n, const char& __c)
+ __fill_n_aux(char* __first, _Size __n, const char& __c)
{
- std::fill(__first, __first + __n, __c);
+ std::__fill_aux(__first, __first + __n, __c);
return __first + __n;
}
+#ifdef _GLIBCXX_USE_WCHAR_T
+ template<typename _Size>
+ inline wchar_t*
+ __fill_n_aux(wchar_t* __first, _Size __n, const wchar_t& __c)
+ {
+ std::__fill_aux(__first, __first + __n, __c);
+ return __first + __n;
+ }
+#endif
+
+ template<bool>
+ struct __fill_n_normal
+ {
+ template<typename _OI, typename _Size, typename _Tp>
+ static _OI
+ __fill_n_n(_OI __first, _Size __n, const _Tp& __value)
+ { return std::__fill_n_aux(__first, __n, __value); }
+ };
+
+ template<>
+ struct __fill_n_normal<true>
+ {
+ template<typename _OI, typename _Size, typename _Tp>
+ static _OI
+ __fill_n_n(_OI __first, _Size __n, const _Tp& __value)
+ { return _OI(std::__fill_n_aux(__first.base(), __n, __value)); }
+ };
+
+ /**
+ * @brief Fills the range [first,first+n) with copies of value.
+ * @param first An output iterator.
+ * @param n The count of copies to perform.
+ * @param value A reference-to-const of arbitrary type.
+ * @return The iterator at first+n.
+ *
+ * This function fills a range with copies of the same value. For char
+ * types filling contiguous areas of memory, this becomes an inline call
+ * to @c memset or @ wmemset.
+ */
+ template<typename _OutputIterator, typename _Size, typename _Tp>
+ inline _OutputIterator
+ fill_n(_OutputIterator __first, _Size __n, const _Tp& __value)
+ {
+ // concept requirements
+ __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator, _Tp>)
+
+ const bool __oi = __is_normal_iterator<_OutputIterator>::__value;
+ return std::__fill_n_normal<__oi>::__fill_n_n(__first, __n, __value);
+ }
+
/**
* @brief Finds the places in ranges which don't match.
* @param first1 An input iterator.
#endif /* CHAR_MAX == SCHAR_MAX */
}
-} // namespace std
+_GLIBCXX_END_NAMESPACE
#endif