1 // Raw memory manipulators -*- C++ -*-
3 // Copyright (C) 2001-2016 Free Software Foundation, Inc.
5 // This file is part of the GNU ISO C++ Library. This library is free
6 // software; you can redistribute it and/or modify it under the
7 // terms of the GNU General Public License as published by the
8 // Free Software Foundation; either version 3, or (at your option)
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
16 // Under Section 7 of GPL version 3, you are granted additional
17 // permissions described in the GCC Runtime Library Exception, version
18 // 3.1, as published by the Free Software Foundation.
20 // You should have received a copy of the GNU General Public License and
21 // a copy of the GCC Runtime Library Exception along with this program;
22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23 // <http://www.gnu.org/licenses/>.
28 * Hewlett-Packard Company
30 * Permission to use, copy, modify, distribute and sell this software
31 * and its documentation for any purpose is hereby granted without fee,
32 * provided that the above copyright notice appear in all copies and
33 * that both that copyright notice and this permission notice appear
34 * in supporting documentation. Hewlett-Packard Company makes no
35 * representations about the suitability of this software for any
36 * purpose. It is provided "as is" without express or implied warranty.
39 * Copyright (c) 1996,1997
40 * Silicon Graphics Computer Systems, Inc.
42 * Permission to use, copy, modify, distribute and sell this software
43 * and its documentation for any purpose is hereby granted without fee,
44 * provided that the above copyright notice appear in all copies and
45 * that both that copyright notice and this permission notice appear
46 * in supporting documentation. Silicon Graphics makes no
47 * representations about the suitability of this software for any
48 * purpose. It is provided "as is" without express or implied warranty.
51 /** @file bits/stl_uninitialized.h
52 * This is an internal header file, included by other library headers.
53 * Do not attempt to use it directly. @headername{memory}
56 #ifndef _STL_UNINITIALIZED_H
57 #define _STL_UNINITIALIZED_H 1
59 #if __cplusplus > 201402L
63 namespace std
_GLIBCXX_VISIBILITY(default)
65 _GLIBCXX_BEGIN_NAMESPACE_VERSION
67 template<bool _TrivialValueTypes
>
68 struct __uninitialized_copy
70 template<typename _InputIterator
, typename _ForwardIterator
>
71 static _ForwardIterator
72 __uninit_copy(_InputIterator __first
, _InputIterator __last
,
73 _ForwardIterator __result
)
75 _ForwardIterator __cur
= __result
;
78 for (; __first
!= __last
; ++__first
, (void)++__cur
)
79 std::_Construct(std::__addressof(*__cur
), *__first
);
84 std::_Destroy(__result
, __cur
);
85 __throw_exception_again
;
91 struct __uninitialized_copy
<true>
93 template<typename _InputIterator
, typename _ForwardIterator
>
94 static _ForwardIterator
95 __uninit_copy(_InputIterator __first
, _InputIterator __last
,
96 _ForwardIterator __result
)
97 { return std::copy(__first
, __last
, __result
); }
101 * @brief Copies the range [first,last) into result.
102 * @param __first An input iterator.
103 * @param __last An input iterator.
104 * @param __result An output iterator.
105 * @return __result + (__first - __last)
107 * Like copy(), but does not require an initialized output range.
109 template<typename _InputIterator
, typename _ForwardIterator
>
110 inline _ForwardIterator
111 uninitialized_copy(_InputIterator __first
, _InputIterator __last
,
112 _ForwardIterator __result
)
114 typedef typename iterator_traits
<_InputIterator
>::value_type
116 typedef typename iterator_traits
<_ForwardIterator
>::value_type
118 #if __cplusplus < 201103L
119 const bool __assignable
= true;
121 // trivial types can have deleted assignment
122 typedef typename iterator_traits
<_InputIterator
>::reference _RefType1
;
123 typedef typename iterator_traits
<_ForwardIterator
>::reference _RefType2
;
124 const bool __assignable
= is_assignable
<_RefType2
, _RefType1
>::value
;
127 return std::__uninitialized_copy
<__is_trivial(_ValueType1
)
128 && __is_trivial(_ValueType2
)
130 __uninit_copy(__first
, __last
, __result
);
134 template<bool _TrivialValueType
>
135 struct __uninitialized_fill
137 template<typename _ForwardIterator
, typename _Tp
>
139 __uninit_fill(_ForwardIterator __first
, _ForwardIterator __last
,
142 _ForwardIterator __cur
= __first
;
145 for (; __cur
!= __last
; ++__cur
)
146 std::_Construct(std::__addressof(*__cur
), __x
);
150 std::_Destroy(__first
, __cur
);
151 __throw_exception_again
;
157 struct __uninitialized_fill
<true>
159 template<typename _ForwardIterator
, typename _Tp
>
161 __uninit_fill(_ForwardIterator __first
, _ForwardIterator __last
,
163 { std::fill(__first
, __last
, __x
); }
167 * @brief Copies the value x into the range [first,last).
168 * @param __first An input iterator.
169 * @param __last An input iterator.
170 * @param __x The source value.
173 * Like fill(), but does not require an initialized output range.
175 template<typename _ForwardIterator
, typename _Tp
>
177 uninitialized_fill(_ForwardIterator __first
, _ForwardIterator __last
,
180 typedef typename iterator_traits
<_ForwardIterator
>::value_type
182 #if __cplusplus < 201103L
183 const bool __assignable
= true;
185 // trivial types can have deleted assignment
186 const bool __assignable
= is_copy_assignable
<_ValueType
>::value
;
189 std::__uninitialized_fill
<__is_trivial(_ValueType
) && __assignable
>::
190 __uninit_fill(__first
, __last
, __x
);
194 template<bool _TrivialValueType
>
195 struct __uninitialized_fill_n
197 template<typename _ForwardIterator
, typename _Size
, typename _Tp
>
198 static _ForwardIterator
199 __uninit_fill_n(_ForwardIterator __first
, _Size __n
,
202 _ForwardIterator __cur
= __first
;
205 for (; __n
> 0; --__n
, ++__cur
)
206 std::_Construct(std::__addressof(*__cur
), __x
);
211 std::_Destroy(__first
, __cur
);
212 __throw_exception_again
;
218 struct __uninitialized_fill_n
<true>
220 template<typename _ForwardIterator
, typename _Size
, typename _Tp
>
221 static _ForwardIterator
222 __uninit_fill_n(_ForwardIterator __first
, _Size __n
,
224 { return std::fill_n(__first
, __n
, __x
); }
227 // _GLIBCXX_RESOLVE_LIB_DEFECTS
228 // DR 1339. uninitialized_fill_n should return the end of its range
230 * @brief Copies the value x into the range [first,first+n).
231 * @param __first An input iterator.
232 * @param __n The number of copies to make.
233 * @param __x The source value.
236 * Like fill_n(), but does not require an initialized output range.
238 template<typename _ForwardIterator
, typename _Size
, typename _Tp
>
239 inline _ForwardIterator
240 uninitialized_fill_n(_ForwardIterator __first
, _Size __n
, const _Tp
& __x
)
242 typedef typename iterator_traits
<_ForwardIterator
>::value_type
244 #if __cplusplus < 201103L
245 const bool __assignable
= true;
247 // trivial types can have deleted assignment
248 const bool __assignable
= is_copy_assignable
<_ValueType
>::value
;
250 return __uninitialized_fill_n
<__is_trivial(_ValueType
) && __assignable
>::
251 __uninit_fill_n(__first
, __n
, __x
);
254 // Extensions: versions of uninitialized_copy, uninitialized_fill,
255 // and uninitialized_fill_n that take an allocator parameter.
256 // We dispatch back to the standard versions when we're given the
257 // default allocator. For nondefault allocators we do not use
258 // any of the POD optimizations.
260 template<typename _InputIterator
, typename _ForwardIterator
,
263 __uninitialized_copy_a(_InputIterator __first
, _InputIterator __last
,
264 _ForwardIterator __result
, _Allocator
& __alloc
)
266 _ForwardIterator __cur
= __result
;
269 typedef __gnu_cxx::__alloc_traits
<_Allocator
> __traits
;
270 for (; __first
!= __last
; ++__first
, (void)++__cur
)
271 __traits::construct(__alloc
, std::__addressof(*__cur
), *__first
);
276 std::_Destroy(__result
, __cur
, __alloc
);
277 __throw_exception_again
;
281 template<typename _InputIterator
, typename _ForwardIterator
, typename _Tp
>
282 inline _ForwardIterator
283 __uninitialized_copy_a(_InputIterator __first
, _InputIterator __last
,
284 _ForwardIterator __result
, allocator
<_Tp
>&)
285 { return std::uninitialized_copy(__first
, __last
, __result
); }
287 template<typename _InputIterator
, typename _ForwardIterator
,
289 inline _ForwardIterator
290 __uninitialized_move_a(_InputIterator __first
, _InputIterator __last
,
291 _ForwardIterator __result
, _Allocator
& __alloc
)
293 return std::__uninitialized_copy_a(_GLIBCXX_MAKE_MOVE_ITERATOR(__first
),
294 _GLIBCXX_MAKE_MOVE_ITERATOR(__last
),
298 template<typename _InputIterator
, typename _ForwardIterator
,
300 inline _ForwardIterator
301 __uninitialized_move_if_noexcept_a(_InputIterator __first
,
302 _InputIterator __last
,
303 _ForwardIterator __result
,
306 return std::__uninitialized_copy_a
307 (_GLIBCXX_MAKE_MOVE_IF_NOEXCEPT_ITERATOR(__first
),
308 _GLIBCXX_MAKE_MOVE_IF_NOEXCEPT_ITERATOR(__last
), __result
, __alloc
);
311 template<typename _ForwardIterator
, typename _Tp
, typename _Allocator
>
313 __uninitialized_fill_a(_ForwardIterator __first
, _ForwardIterator __last
,
314 const _Tp
& __x
, _Allocator
& __alloc
)
316 _ForwardIterator __cur
= __first
;
319 typedef __gnu_cxx::__alloc_traits
<_Allocator
> __traits
;
320 for (; __cur
!= __last
; ++__cur
)
321 __traits::construct(__alloc
, std::__addressof(*__cur
), __x
);
325 std::_Destroy(__first
, __cur
, __alloc
);
326 __throw_exception_again
;
330 template<typename _ForwardIterator
, typename _Tp
, typename _Tp2
>
332 __uninitialized_fill_a(_ForwardIterator __first
, _ForwardIterator __last
,
333 const _Tp
& __x
, allocator
<_Tp2
>&)
334 { std::uninitialized_fill(__first
, __last
, __x
); }
336 template<typename _ForwardIterator
, typename _Size
, typename _Tp
,
339 __uninitialized_fill_n_a(_ForwardIterator __first
, _Size __n
,
340 const _Tp
& __x
, _Allocator
& __alloc
)
342 _ForwardIterator __cur
= __first
;
345 typedef __gnu_cxx::__alloc_traits
<_Allocator
> __traits
;
346 for (; __n
> 0; --__n
, ++__cur
)
347 __traits::construct(__alloc
, std::__addressof(*__cur
), __x
);
352 std::_Destroy(__first
, __cur
, __alloc
);
353 __throw_exception_again
;
357 template<typename _ForwardIterator
, typename _Size
, typename _Tp
,
359 inline _ForwardIterator
360 __uninitialized_fill_n_a(_ForwardIterator __first
, _Size __n
,
361 const _Tp
& __x
, allocator
<_Tp2
>&)
362 { return std::uninitialized_fill_n(__first
, __n
, __x
); }
365 // Extensions: __uninitialized_copy_move, __uninitialized_move_copy,
366 // __uninitialized_fill_move, __uninitialized_move_fill.
367 // All of these algorithms take a user-supplied allocator, which is used
368 // for construction and destruction.
370 // __uninitialized_copy_move
371 // Copies [first1, last1) into [result, result + (last1 - first1)), and
372 // move [first2, last2) into
373 // [result, result + (last1 - first1) + (last2 - first2)).
374 template<typename _InputIterator1
, typename _InputIterator2
,
375 typename _ForwardIterator
, typename _Allocator
>
376 inline _ForwardIterator
377 __uninitialized_copy_move(_InputIterator1 __first1
,
378 _InputIterator1 __last1
,
379 _InputIterator2 __first2
,
380 _InputIterator2 __last2
,
381 _ForwardIterator __result
,
384 _ForwardIterator __mid
= std::__uninitialized_copy_a(__first1
, __last1
,
389 return std::__uninitialized_move_a(__first2
, __last2
, __mid
, __alloc
);
393 std::_Destroy(__result
, __mid
, __alloc
);
394 __throw_exception_again
;
398 // __uninitialized_move_copy
399 // Moves [first1, last1) into [result, result + (last1 - first1)), and
400 // copies [first2, last2) into
401 // [result, result + (last1 - first1) + (last2 - first2)).
402 template<typename _InputIterator1
, typename _InputIterator2
,
403 typename _ForwardIterator
, typename _Allocator
>
404 inline _ForwardIterator
405 __uninitialized_move_copy(_InputIterator1 __first1
,
406 _InputIterator1 __last1
,
407 _InputIterator2 __first2
,
408 _InputIterator2 __last2
,
409 _ForwardIterator __result
,
412 _ForwardIterator __mid
= std::__uninitialized_move_a(__first1
, __last1
,
417 return std::__uninitialized_copy_a(__first2
, __last2
, __mid
, __alloc
);
421 std::_Destroy(__result
, __mid
, __alloc
);
422 __throw_exception_again
;
426 // __uninitialized_fill_move
427 // Fills [result, mid) with x, and moves [first, last) into
428 // [mid, mid + (last - first)).
429 template<typename _ForwardIterator
, typename _Tp
, typename _InputIterator
,
431 inline _ForwardIterator
432 __uninitialized_fill_move(_ForwardIterator __result
, _ForwardIterator __mid
,
433 const _Tp
& __x
, _InputIterator __first
,
434 _InputIterator __last
, _Allocator
& __alloc
)
436 std::__uninitialized_fill_a(__result
, __mid
, __x
, __alloc
);
439 return std::__uninitialized_move_a(__first
, __last
, __mid
, __alloc
);
443 std::_Destroy(__result
, __mid
, __alloc
);
444 __throw_exception_again
;
448 // __uninitialized_move_fill
449 // Moves [first1, last1) into [first2, first2 + (last1 - first1)), and
450 // fills [first2 + (last1 - first1), last2) with x.
451 template<typename _InputIterator
, typename _ForwardIterator
, typename _Tp
,
454 __uninitialized_move_fill(_InputIterator __first1
, _InputIterator __last1
,
455 _ForwardIterator __first2
,
456 _ForwardIterator __last2
, const _Tp
& __x
,
459 _ForwardIterator __mid2
= std::__uninitialized_move_a(__first1
, __last1
,
464 std::__uninitialized_fill_a(__mid2
, __last2
, __x
, __alloc
);
468 std::_Destroy(__first2
, __mid2
, __alloc
);
469 __throw_exception_again
;
473 #if __cplusplus >= 201103L
474 // Extensions: __uninitialized_default, __uninitialized_default_n,
475 // __uninitialized_default_a, __uninitialized_default_n_a.
477 template<bool _TrivialValueType
>
478 struct __uninitialized_default_1
480 template<typename _ForwardIterator
>
482 __uninit_default(_ForwardIterator __first
, _ForwardIterator __last
)
484 _ForwardIterator __cur
= __first
;
487 for (; __cur
!= __last
; ++__cur
)
488 std::_Construct(std::__addressof(*__cur
));
492 std::_Destroy(__first
, __cur
);
493 __throw_exception_again
;
499 struct __uninitialized_default_1
<true>
501 template<typename _ForwardIterator
>
503 __uninit_default(_ForwardIterator __first
, _ForwardIterator __last
)
505 typedef typename iterator_traits
<_ForwardIterator
>::value_type
508 std::fill(__first
, __last
, _ValueType());
512 template<bool _TrivialValueType
>
513 struct __uninitialized_default_n_1
515 template<typename _ForwardIterator
, typename _Size
>
516 static _ForwardIterator
517 __uninit_default_n(_ForwardIterator __first
, _Size __n
)
519 _ForwardIterator __cur
= __first
;
522 for (; __n
> 0; --__n
, ++__cur
)
523 std::_Construct(std::__addressof(*__cur
));
528 std::_Destroy(__first
, __cur
);
529 __throw_exception_again
;
535 struct __uninitialized_default_n_1
<true>
537 template<typename _ForwardIterator
, typename _Size
>
538 static _ForwardIterator
539 __uninit_default_n(_ForwardIterator __first
, _Size __n
)
541 typedef typename iterator_traits
<_ForwardIterator
>::value_type
544 return std::fill_n(__first
, __n
, _ValueType());
548 // __uninitialized_default
549 // Fills [first, last) with std::distance(first, last) default
550 // constructed value_types(s).
551 template<typename _ForwardIterator
>
553 __uninitialized_default(_ForwardIterator __first
,
554 _ForwardIterator __last
)
556 typedef typename iterator_traits
<_ForwardIterator
>::value_type
558 // trivial types can have deleted assignment
559 const bool __assignable
= is_copy_assignable
<_ValueType
>::value
;
561 std::__uninitialized_default_1
<__is_trivial(_ValueType
)
563 __uninit_default(__first
, __last
);
566 // __uninitialized_default_n
567 // Fills [first, first + n) with n default constructed value_type(s).
568 template<typename _ForwardIterator
, typename _Size
>
569 inline _ForwardIterator
570 __uninitialized_default_n(_ForwardIterator __first
, _Size __n
)
572 typedef typename iterator_traits
<_ForwardIterator
>::value_type
574 // trivial types can have deleted assignment
575 const bool __assignable
= is_copy_assignable
<_ValueType
>::value
;
577 return __uninitialized_default_n_1
<__is_trivial(_ValueType
)
579 __uninit_default_n(__first
, __n
);
583 // __uninitialized_default_a
584 // Fills [first, last) with std::distance(first, last) default
585 // constructed value_types(s), constructed with the allocator alloc.
586 template<typename _ForwardIterator
, typename _Allocator
>
588 __uninitialized_default_a(_ForwardIterator __first
,
589 _ForwardIterator __last
,
592 _ForwardIterator __cur
= __first
;
595 typedef __gnu_cxx::__alloc_traits
<_Allocator
> __traits
;
596 for (; __cur
!= __last
; ++__cur
)
597 __traits::construct(__alloc
, std::__addressof(*__cur
));
601 std::_Destroy(__first
, __cur
, __alloc
);
602 __throw_exception_again
;
606 template<typename _ForwardIterator
, typename _Tp
>
608 __uninitialized_default_a(_ForwardIterator __first
,
609 _ForwardIterator __last
,
611 { std::__uninitialized_default(__first
, __last
); }
614 // __uninitialized_default_n_a
615 // Fills [first, first + n) with n default constructed value_types(s),
616 // constructed with the allocator alloc.
617 template<typename _ForwardIterator
, typename _Size
, typename _Allocator
>
619 __uninitialized_default_n_a(_ForwardIterator __first
, _Size __n
,
622 _ForwardIterator __cur
= __first
;
625 typedef __gnu_cxx::__alloc_traits
<_Allocator
> __traits
;
626 for (; __n
> 0; --__n
, ++__cur
)
627 __traits::construct(__alloc
, std::__addressof(*__cur
));
632 std::_Destroy(__first
, __cur
, __alloc
);
633 __throw_exception_again
;
637 template<typename _ForwardIterator
, typename _Size
, typename _Tp
>
638 inline _ForwardIterator
639 __uninitialized_default_n_a(_ForwardIterator __first
, _Size __n
,
641 { return std::__uninitialized_default_n(__first
, __n
); }
644 template<typename _InputIterator
, typename _Size
,
645 typename _ForwardIterator
>
647 __uninitialized_copy_n(_InputIterator __first
, _Size __n
,
648 _ForwardIterator __result
, input_iterator_tag
)
650 _ForwardIterator __cur
= __result
;
653 for (; __n
> 0; --__n
, ++__first
, ++__cur
)
654 std::_Construct(std::__addressof(*__cur
), *__first
);
659 std::_Destroy(__result
, __cur
);
660 __throw_exception_again
;
664 template<typename _RandomAccessIterator
, typename _Size
,
665 typename _ForwardIterator
>
666 inline _ForwardIterator
667 __uninitialized_copy_n(_RandomAccessIterator __first
, _Size __n
,
668 _ForwardIterator __result
,
669 random_access_iterator_tag
)
670 { return std::uninitialized_copy(__first
, __first
+ __n
, __result
); }
673 * @brief Copies the range [first,first+n) into result.
674 * @param __first An input iterator.
675 * @param __n The number of elements to copy.
676 * @param __result An output iterator.
677 * @return __result + __n
679 * Like copy_n(), but does not require an initialized output range.
681 template<typename _InputIterator
, typename _Size
, typename _ForwardIterator
>
682 inline _ForwardIterator
683 uninitialized_copy_n(_InputIterator __first
, _Size __n
,
684 _ForwardIterator __result
)
685 { return std::__uninitialized_copy_n(__first
, __n
, __result
,
686 std::__iterator_category(__first
)); }
689 #if __cplusplus > 201402L
690 template <typename _ForwardIterator
>
692 uninitialized_default_construct(_ForwardIterator __first
,
693 _ForwardIterator __last
)
695 for (; __first
!= __last
; ++__first
)
696 ::new (static_cast<void*>(std::__addressof(*__first
)))
697 typename iterator_traits
<_ForwardIterator
>::value_type
;
700 template <typename _ForwardIterator
, typename _Size
>
701 inline _ForwardIterator
702 uninitialized_default_construct_n(_ForwardIterator __first
, _Size __count
)
704 for (; __count
> 0; (void)++__first
, --__count
)
705 ::new (static_cast<void*>(std::__addressof(*__first
)))
706 typename iterator_traits
<_ForwardIterator
>::value_type
;
710 template <typename _ForwardIterator
>
712 uninitialized_value_construct(_ForwardIterator __first
,
713 _ForwardIterator __last
)
715 for (; __first
!= __last
; ++__first
)
716 ::new (static_cast<void*>(std::__addressof(*__first
)))
717 typename iterator_traits
<_ForwardIterator
>::value_type();
720 template <typename _ForwardIterator
, typename _Size
>
721 inline _ForwardIterator
722 uninitialized_value_construct_n(_ForwardIterator __first
, _Size __count
)
724 for (; __count
> 0; (void)++__first
, --__count
)
725 ::new (static_cast<void*>(std::__addressof(*__first
)))
726 typename iterator_traits
<_ForwardIterator
>::value_type();
730 template <typename _InputIterator
, typename _ForwardIterator
>
731 inline _ForwardIterator
732 uninitialized_move(_InputIterator __first
, _InputIterator __last
,
733 _ForwardIterator __result
)
735 for (; __first
!= __last
; (void)++__result
, ++__first
)
736 ::new (static_cast<void*>(std::__addressof(*__result
)))
738 iterator_traits
<_ForwardIterator
>::value_type(std::move(*__first
));
742 template <typename _InputIterator
, typename _Size
, typename _ForwardIterator
>
743 inline pair
<_InputIterator
, _ForwardIterator
>
744 uninitialized_move_n(_InputIterator __first
, _Size __count
,
745 _ForwardIterator __result
)
747 for (; __count
> 0; ++__result
, (void) ++__first
, --__count
)
748 ::new (static_cast<void*>(std::__addressof(*__result
)))
750 iterator_traits
<_ForwardIterator
>::value_type(std::move(*__first
));
751 return {__first
, __result
};
754 template <typename _Tp
>
756 destroy_at(_Tp
* __location
)
761 template <typename _ForwardIterator
>
763 destroy(_ForwardIterator __first
, _ForwardIterator __last
)
765 for (; __first
!= __last
; ++__first
)
766 std::destroy_at(std::__addressof(*__first
));
769 template <typename _ForwardIterator
, typename _Size
>
770 inline _ForwardIterator
771 destroy_n(_ForwardIterator __first
, _Size __count
)
773 for (; __count
> 0; (void)++__first
, --__count
)
774 std::destroy_at(std::__addressof(*__first
));
781 _GLIBCXX_END_NAMESPACE_VERSION
784 #endif /* _STL_UNINITIALIZED_H */