@@ -1996,14 +1996,51 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
19961996 return this ->insert_range_impl (pos, rg, n).pos ;
19971997 }
19981998
1999+ private:
2000+ template <bool isprepend>
2001+ struct prepend_or_append_range_guard
2002+ {
2003+ deque *thisdeq{};
2004+ size_type oldn{};
2005+ constexpr ~prepend_or_append_range_guard ()
2006+ {
2007+ if (thisdeq)
2008+ {
2009+ if constexpr (isprepend)
2010+ {
2011+ thisdeq->erase (thisdeq->cbegin (), thisdeq->cend () - oldn);
2012+ }
2013+ else
2014+ {
2015+ thisdeq->erase (thisdeq->cbegin () + oldn, thisdeq->cend ());
2016+ }
2017+ }
2018+ }
2019+ };
2020+ using append_range_guard = prepend_or_append_range_guard<false >;
2021+ using prepend_range_guard = prepend_or_append_range_guard<true >;
2022+
2023+ public:
19992024 template <::std::ranges::range R>
20002025 requires ::std::constructible_from<value_type, ::std::ranges::range_value_t <R>>
20012026 inline constexpr void append_range (R &&rg) noexcept (::std::is_nothrow_constructible_v<value_type, ::std::ranges::range_value_t <R>>)
20022027 {
20032028 // To do: cleanup code
2004- for (auto &e : rg)
2029+ if constexpr (::std::is_nothrow_constructible_v<value_type, ::std::ranges::range_value_t <R>>)
2030+ {
2031+ for (auto &e : rg)
2032+ {
2033+ this ->push_back (e);
2034+ }
2035+ }
2036+ else
20052037 {
2006- this ->push_back (e);
2038+ append_range_guard guard{this , this ->size ()};
2039+ for (auto &e : rg)
2040+ {
2041+ this ->push_back (e);
2042+ }
2043+ guard.thisdeq = nullptr ;
20072044 }
20082045 }
20092046#if 0
@@ -2019,15 +2056,37 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
20192056 }
20202057 return this->size() - old_size;
20212058 }
2059+ #endif
20222060public:
20232061 template <::std::ranges::range R>
20242062 requires ::std::constructible_from<value_type, ::std::ranges::range_value_t <R>>
2025- inline constexpr void prepend_range(R &&rg) noexcept(::std::is_nothrow_constructible_v<value_type, ::std::ranges::range_value_t<R>>)
2063+ inline constexpr void prepend_range (R &&rg) noexcept (
2064+ ::std::is_nothrow_constructible_v<value_type, ::std::ranges::range_value_t <R>> &&
2065+ ::std::is_nothrow_swappable_v<value_type>)
20262066 {
20272067 // To do: cleanup code
2028- this->prepend_range_impl(::std::forward<R>(rg));
2068+ size_type oldn{this ->size ()};
2069+ if constexpr (
2070+ ::std::is_nothrow_constructible_v<value_type, ::std::ranges::range_value_t <R>> &&
2071+ ::std::is_nothrow_swappable_v<value_type>)
2072+ {
2073+ for (auto &e : rg)
2074+ {
2075+ this ->push_front (e);
2076+ }
2077+ ::std::reverse (this ->begin (), this->end() - oldn);
2078+ }
2079+ else
2080+ {
2081+ prepend_range_guard guard{this , oldn};
2082+ for (auto &e : rg)
2083+ {
2084+ this ->push_front (e);
2085+ }
2086+ ::std::reverse (this ->begin (), this->end() - oldn);
2087+ guard.thisdeq = nullptr ;
2088+ }
20292089 }
2030- #endif
20312090
20322091private:
20332092 inline constexpr iterator erase_no_destroy_common_impl (iterator first, iterator last, bool moveleft) noexcept
@@ -2064,7 +2123,6 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
20642123 {
20652124 this ->destroy_elements_range (first, last);
20662125 }
2067- #if 1
20682126 if constexpr (::fast_io::freestanding::is_trivially_copyable_or_relocatable_v<value_type>)
20692127 {
20702128 if !consteval
@@ -2078,7 +2136,6 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
20782136 ::std::bit_cast<::fast_io::containers::details::deque_control_block_common>(last.itercontent), moveleft, blockbytes));
20792137 }
20802138 }
2081- #endif
20822139 return this ->erase_no_destroy_common_impl (first, last, moveleft);
20832140 }
20842141 inline constexpr iterator erase_unchecked_single_impl (iterator pos, bool moveleft) noexcept
@@ -2087,7 +2144,6 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
20872144 {
20882145 ::std::destroy (pos.itercontent.curr_ptr);
20892146 }
2090- #if 1
20912147 if constexpr (::fast_io::freestanding::is_trivially_copyable_or_relocatable_v<value_type>)
20922148 {
20932149 if !consteval
@@ -2109,7 +2165,6 @@ class deque FAST_IO_TRIVIALLY_RELOCATABLE_IF_ELIGIBLE
21092165 ::std::bit_cast<::fast_io::containers::details::deque_control_block_common>(posp1), moveleft, blockbytes));
21102166 }
21112167 }
2112- #endif
21132168 auto posp1{pos};
21142169 ++posp1;
21152170 return this ->erase_no_destroy_common_impl (pos, posp1, moveleft);
0 commit comments