1 // Raw memory manipulators -*- C++ -*-
3 // Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008,
5 // Free Software Foundation, Inc.
7 // This file is part of the GNU ISO C++ Library. This library is free
8 // software; you can redistribute it and/or modify it under the
9 // terms of the GNU General Public License as published by the
10 // Free Software Foundation; either version 3, or (at your option)
13 // This library is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 // GNU General Public License for more details.
18 // Under Section 7 of GPL version 3, you are granted additional
19 // permissions described in the GCC Runtime Library Exception, version
20 // 3.1, as published by the Free Software Foundation.
22 // You should have received a copy of the GNU General Public License and
23 // a copy of the GCC Runtime Library Exception along with this program;
24 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
25 // <http://www.gnu.org/licenses/>.
30 * Hewlett-Packard Company
32 * Permission to use, copy, modify, distribute and sell this software
33 * and its documentation for any purpose is hereby granted without fee,
34 * provided that the above copyright notice appear in all copies and
35 * that both that copyright notice and this permission notice appear
36 * in supporting documentation. Hewlett-Packard Company makes no
37 * representations about the suitability of this software for any
38 * purpose. It is provided "as is" without express or implied warranty.
41 * Copyright (c) 1996,1997
42 * Silicon Graphics Computer Systems, Inc.
44 * Permission to use, copy, modify, distribute and sell this software
45 * and its documentation for any purpose is hereby granted without fee,
46 * provided that the above copyright notice appear in all copies and
47 * that both that copyright notice and this permission notice appear
48 * in supporting documentation. Silicon Graphics makes no
49 * representations about the suitability of this software for any
50 * purpose. It is provided "as is" without express or implied warranty.
53 /** @file bits/stl_uninitialized.h
54 * This is an internal header file, included by other library headers.
55 * Do not attempt to use it directly. @headername{memory}
58 #ifndef _STL_UNINITIALIZED_H
59 #define _STL_UNINITIALIZED_H 1
61 namespace std _GLIBCXX_VISIBILITY(default)
63 _GLIBCXX_BEGIN_NAMESPACE_VERSION
65 template<bool _TrivialValueTypes>
66 struct __uninitialized_copy
68 template<typename _InputIterator, typename _ForwardIterator>
69 static _ForwardIterator
70 __uninit_copy(_InputIterator __first, _InputIterator __last,
71 _ForwardIterator __result)
73 _ForwardIterator __cur = __result;
76 for (; __first != __last; ++__first, ++__cur)
77 std::_Construct(std::__addressof(*__cur), *__first);
82 std::_Destroy(__result, __cur);
83 __throw_exception_again;
89 struct __uninitialized_copy<true>
91 template<typename _InputIterator, typename _ForwardIterator>
92 static _ForwardIterator
93 __uninit_copy(_InputIterator __first, _InputIterator __last,
94 _ForwardIterator __result)
95 { return std::copy(__first, __last, __result); }
99 * @brief Copies the range [first,last) into result.
100 * @param first An input iterator.
101 * @param last An input iterator.
102 * @param result An output iterator.
103 * @return result + (first - last)
105 * Like copy(), but does not require an initialized output range.
107 template<typename _InputIterator, typename _ForwardIterator>
108 inline _ForwardIterator
109 uninitialized_copy(_InputIterator __first, _InputIterator __last,
110 _ForwardIterator __result)
112 typedef typename iterator_traits<_InputIterator>::value_type
114 typedef typename iterator_traits<_ForwardIterator>::value_type
117 return std::__uninitialized_copy<(__is_trivial(_ValueType1)
118 && __is_trivial(_ValueType2))>::
119 __uninit_copy(__first, __last, __result);
123 template<bool _TrivialValueType>
124 struct __uninitialized_fill
126 template<typename _ForwardIterator, typename _Tp>
128 __uninit_fill(_ForwardIterator __first, _ForwardIterator __last,
131 _ForwardIterator __cur = __first;
134 for (; __cur != __last; ++__cur)
135 std::_Construct(std::__addressof(*__cur), __x);
139 std::_Destroy(__first, __cur);
140 __throw_exception_again;
146 struct __uninitialized_fill<true>
148 template<typename _ForwardIterator, typename _Tp>
150 __uninit_fill(_ForwardIterator __first, _ForwardIterator __last,
152 { std::fill(__first, __last, __x); }
156 * @brief Copies the value x into the range [first,last).
157 * @param first An input iterator.
158 * @param last An input iterator.
159 * @param x The source value.
162 * Like fill(), but does not require an initialized output range.
164 template<typename _ForwardIterator, typename _Tp>
166 uninitialized_fill(_ForwardIterator __first, _ForwardIterator __last,
169 typedef typename iterator_traits<_ForwardIterator>::value_type
172 std::__uninitialized_fill<__is_trivial(_ValueType)>::
173 __uninit_fill(__first, __last, __x);
177 template<bool _TrivialValueType>
178 struct __uninitialized_fill_n
180 template<typename _ForwardIterator, typename _Size, typename _Tp>
182 __uninit_fill_n(_ForwardIterator __first, _Size __n,
185 _ForwardIterator __cur = __first;
188 for (; __n > 0; --__n, ++__cur)
189 std::_Construct(std::__addressof(*__cur), __x);
193 std::_Destroy(__first, __cur);
194 __throw_exception_again;
200 struct __uninitialized_fill_n<true>
202 template<typename _ForwardIterator, typename _Size, typename _Tp>
204 __uninit_fill_n(_ForwardIterator __first, _Size __n,
206 { std::fill_n(__first, __n, __x); }
210 * @brief Copies the value x into the range [first,first+n).
211 * @param first An input iterator.
212 * @param n The number of copies to make.
213 * @param x The source value.
216 * Like fill_n(), but does not require an initialized output range.
218 template<typename _ForwardIterator, typename _Size, typename _Tp>
220 uninitialized_fill_n(_ForwardIterator __first, _Size __n, const _Tp& __x)
222 typedef typename iterator_traits<_ForwardIterator>::value_type
225 std::__uninitialized_fill_n<__is_trivial(_ValueType)>::
226 __uninit_fill_n(__first, __n, __x);
229 // Extensions: versions of uninitialized_copy, uninitialized_fill,
230 // and uninitialized_fill_n that take an allocator parameter.
231 // We dispatch back to the standard versions when we're given the
232 // default allocator. For nondefault allocators we do not use
233 // any of the POD optimizations.
235 template<typename _InputIterator, typename _ForwardIterator,
238 __uninitialized_copy_a(_InputIterator __first, _InputIterator __last,
239 _ForwardIterator __result, _Allocator& __alloc)
241 _ForwardIterator __cur = __result;
244 for (; __first != __last; ++__first, ++__cur)
245 __alloc.construct(std::__addressof(*__cur), *__first);
250 std::_Destroy(__result, __cur, __alloc);
251 __throw_exception_again;
255 template<typename _InputIterator, typename _ForwardIterator, typename _Tp>
256 inline _ForwardIterator
257 __uninitialized_copy_a(_InputIterator __first, _InputIterator __last,
258 _ForwardIterator __result, allocator<_Tp>&)
259 { return std::uninitialized_copy(__first, __last, __result); }
261 template<typename _InputIterator, typename _ForwardIterator,
263 inline _ForwardIterator
264 __uninitialized_move_a(_InputIterator __first, _InputIterator __last,
265 _ForwardIterator __result, _Allocator& __alloc)
267 return std::__uninitialized_copy_a(_GLIBCXX_MAKE_MOVE_ITERATOR(__first),
268 _GLIBCXX_MAKE_MOVE_ITERATOR(__last),
272 template<typename _InputIterator, typename _ForwardIterator,
274 inline _ForwardIterator
275 __uninitialized_move_if_noexcept_a(_InputIterator __first,
276 _InputIterator __last,
277 _ForwardIterator __result,
280 return std::__uninitialized_copy_a
281 (_GLIBCXX_MAKE_MOVE_IF_NOEXCEPT_ITERATOR(__first),
282 _GLIBCXX_MAKE_MOVE_IF_NOEXCEPT_ITERATOR(__last), __result, __alloc);
285 template<typename _ForwardIterator, typename _Tp, typename _Allocator>
287 __uninitialized_fill_a(_ForwardIterator __first, _ForwardIterator __last,
288 const _Tp& __x, _Allocator& __alloc)
290 _ForwardIterator __cur = __first;
293 for (; __cur != __last; ++__cur)
294 __alloc.construct(std::__addressof(*__cur), __x);
298 std::_Destroy(__first, __cur, __alloc);
299 __throw_exception_again;
303 template<typename _ForwardIterator, typename _Tp, typename _Tp2>
305 __uninitialized_fill_a(_ForwardIterator __first, _ForwardIterator __last,
306 const _Tp& __x, allocator<_Tp2>&)
307 { std::uninitialized_fill(__first, __last, __x); }
309 template<typename _ForwardIterator, typename _Size, typename _Tp,
312 __uninitialized_fill_n_a(_ForwardIterator __first, _Size __n,
313 const _Tp& __x, _Allocator& __alloc)
315 _ForwardIterator __cur = __first;
318 for (; __n > 0; --__n, ++__cur)
319 __alloc.construct(std::__addressof(*__cur), __x);
323 std::_Destroy(__first, __cur, __alloc);
324 __throw_exception_again;
328 template<typename _ForwardIterator, typename _Size, typename _Tp,
331 __uninitialized_fill_n_a(_ForwardIterator __first, _Size __n,
332 const _Tp& __x, allocator<_Tp2>&)
333 { std::uninitialized_fill_n(__first, __n, __x); }
336 // Extensions: __uninitialized_copy_move, __uninitialized_move_copy,
337 // __uninitialized_fill_move, __uninitialized_move_fill.
338 // All of these algorithms take a user-supplied allocator, which is used
339 // for construction and destruction.
341 // __uninitialized_copy_move
342 // Copies [first1, last1) into [result, result + (last1 - first1)), and
343 // move [first2, last2) into
344 // [result, result + (last1 - first1) + (last2 - first2)).
345 template<typename _InputIterator1, typename _InputIterator2,
346 typename _ForwardIterator, typename _Allocator>
347 inline _ForwardIterator
348 __uninitialized_copy_move(_InputIterator1 __first1,
349 _InputIterator1 __last1,
350 _InputIterator2 __first2,
351 _InputIterator2 __last2,
352 _ForwardIterator __result,
355 _ForwardIterator __mid = std::__uninitialized_copy_a(__first1, __last1,
360 return std::__uninitialized_move_a(__first2, __last2, __mid, __alloc);
364 std::_Destroy(__result, __mid, __alloc);
365 __throw_exception_again;
369 // __uninitialized_move_copy
370 // Moves [first1, last1) into [result, result + (last1 - first1)), and
371 // copies [first2, last2) into
372 // [result, result + (last1 - first1) + (last2 - first2)).
373 template<typename _InputIterator1, typename _InputIterator2,
374 typename _ForwardIterator, typename _Allocator>
375 inline _ForwardIterator
376 __uninitialized_move_copy(_InputIterator1 __first1,
377 _InputIterator1 __last1,
378 _InputIterator2 __first2,
379 _InputIterator2 __last2,
380 _ForwardIterator __result,
383 _ForwardIterator __mid = std::__uninitialized_move_a(__first1, __last1,
388 return std::__uninitialized_copy_a(__first2, __last2, __mid, __alloc);
392 std::_Destroy(__result, __mid, __alloc);
393 __throw_exception_again;
397 // __uninitialized_fill_move
398 // Fills [result, mid) with x, and moves [first, last) into
399 // [mid, mid + (last - first)).
400 template<typename _ForwardIterator, typename _Tp, typename _InputIterator,
402 inline _ForwardIterator
403 __uninitialized_fill_move(_ForwardIterator __result, _ForwardIterator __mid,
404 const _Tp& __x, _InputIterator __first,
405 _InputIterator __last, _Allocator& __alloc)
407 std::__uninitialized_fill_a(__result, __mid, __x, __alloc);
410 return std::__uninitialized_move_a(__first, __last, __mid, __alloc);
414 std::_Destroy(__result, __mid, __alloc);
415 __throw_exception_again;
419 // __uninitialized_move_fill
420 // Moves [first1, last1) into [first2, first2 + (last1 - first1)), and
421 // fills [first2 + (last1 - first1), last2) with x.
422 template<typename _InputIterator, typename _ForwardIterator, typename _Tp,
425 __uninitialized_move_fill(_InputIterator __first1, _InputIterator __last1,
426 _ForwardIterator __first2,
427 _ForwardIterator __last2, const _Tp& __x,
430 _ForwardIterator __mid2 = std::__uninitialized_move_a(__first1, __last1,
435 std::__uninitialized_fill_a(__mid2, __last2, __x, __alloc);
439 std::_Destroy(__first2, __mid2, __alloc);
440 __throw_exception_again;
444 #ifdef __GXX_EXPERIMENTAL_CXX0X__
445 // Extensions: __uninitialized_default, __uninitialized_default_n,
446 // __uninitialized_default_a, __uninitialized_default_n_a.
448 template<bool _TrivialValueType>
449 struct __uninitialized_default_1
451 template<typename _ForwardIterator>
453 __uninit_default(_ForwardIterator __first, _ForwardIterator __last)
455 _ForwardIterator __cur = __first;
458 for (; __cur != __last; ++__cur)
459 std::_Construct(std::__addressof(*__cur));
463 std::_Destroy(__first, __cur);
464 __throw_exception_again;
470 struct __uninitialized_default_1<true>
472 template<typename _ForwardIterator>
474 __uninit_default(_ForwardIterator __first, _ForwardIterator __last)
476 typedef typename iterator_traits<_ForwardIterator>::value_type
479 std::fill(__first, __last, _ValueType());
483 template<bool _TrivialValueType>
484 struct __uninitialized_default_n_1
486 template<typename _ForwardIterator, typename _Size>
488 __uninit_default_n(_ForwardIterator __first, _Size __n)
490 _ForwardIterator __cur = __first;
493 for (; __n > 0; --__n, ++__cur)
494 std::_Construct(std::__addressof(*__cur));
498 std::_Destroy(__first, __cur);
499 __throw_exception_again;
505 struct __uninitialized_default_n_1<true>
507 template<typename _ForwardIterator, typename _Size>
509 __uninit_default_n(_ForwardIterator __first, _Size __n)
511 typedef typename iterator_traits<_ForwardIterator>::value_type
514 std::fill_n(__first, __n, _ValueType());
518 // __uninitialized_default
519 // Fills [first, last) with std::distance(first, last) default
520 // constructed value_types(s).
521 template<typename _ForwardIterator>
523 __uninitialized_default(_ForwardIterator __first,
524 _ForwardIterator __last)
526 typedef typename iterator_traits<_ForwardIterator>::value_type
529 std::__uninitialized_default_1<__is_trivial(_ValueType)>::
530 __uninit_default(__first, __last);
533 // __uninitialized_default_n
534 // Fills [first, first + n) with n default constructed value_type(s).
535 template<typename _ForwardIterator, typename _Size>
537 __uninitialized_default_n(_ForwardIterator __first, _Size __n)
539 typedef typename iterator_traits<_ForwardIterator>::value_type
542 std::__uninitialized_default_n_1<__is_trivial(_ValueType)>::
543 __uninit_default_n(__first, __n);
547 // __uninitialized_default_a
548 // Fills [first, last) with std::distance(first, last) default
549 // constructed value_types(s), constructed with the allocator alloc.
550 template<typename _ForwardIterator, typename _Allocator>
552 __uninitialized_default_a(_ForwardIterator __first,
553 _ForwardIterator __last,
556 _ForwardIterator __cur = __first;
559 for (; __cur != __last; ++__cur)
560 __alloc.construct(std::__addressof(*__cur));
564 std::_Destroy(__first, __cur, __alloc);
565 __throw_exception_again;
569 template<typename _ForwardIterator, typename _Tp>
571 __uninitialized_default_a(_ForwardIterator __first,
572 _ForwardIterator __last,
574 { std::__uninitialized_default(__first, __last); }
577 // __uninitialized_default_n_a
578 // Fills [first, first + n) with n default constructed value_types(s),
579 // constructed with the allocator alloc.
580 template<typename _ForwardIterator, typename _Size, typename _Allocator>
582 __uninitialized_default_n_a(_ForwardIterator __first, _Size __n,
585 _ForwardIterator __cur = __first;
588 for (; __n > 0; --__n, ++__cur)
589 __alloc.construct(std::__addressof(*__cur));
593 std::_Destroy(__first, __cur, __alloc);
594 __throw_exception_again;
598 template<typename _ForwardIterator, typename _Size, typename _Tp>
600 __uninitialized_default_n_a(_ForwardIterator __first, _Size __n,
602 { std::__uninitialized_default_n(__first, __n); }
605 template<typename _InputIterator, typename _Size,
606 typename _ForwardIterator>
608 __uninitialized_copy_n(_InputIterator __first, _Size __n,
609 _ForwardIterator __result, input_iterator_tag)
611 _ForwardIterator __cur = __result;
614 for (; __n > 0; --__n, ++__first, ++__cur)
615 std::_Construct(std::__addressof(*__cur), *__first);
620 std::_Destroy(__result, __cur);
621 __throw_exception_again;
625 template<typename _RandomAccessIterator, typename _Size,
626 typename _ForwardIterator>
627 inline _ForwardIterator
628 __uninitialized_copy_n(_RandomAccessIterator __first, _Size __n,
629 _ForwardIterator __result,
630 random_access_iterator_tag)
631 { return std::uninitialized_copy(__first, __first + __n, __result); }
634 * @brief Copies the range [first,first+n) into result.
635 * @param first An input iterator.
636 * @param n The number of elements to copy.
637 * @param result An output iterator.
640 * Like copy_n(), but does not require an initialized output range.
642 template<typename _InputIterator, typename _Size, typename _ForwardIterator>
643 inline _ForwardIterator
644 uninitialized_copy_n(_InputIterator __first, _Size __n,
645 _ForwardIterator __result)
646 { return std::__uninitialized_copy_n(__first, __n, __result,
647 std::__iterator_category(__first)); }
650 _GLIBCXX_END_NAMESPACE_VERSION
653 #endif /* _STL_UNINITIALIZED_H */