11use core:: iter:: { Copied , Rev , TrustedLen } ;
22use core:: slice;
33
4- use super :: VecDeque ;
4+ use super :: { Drain , VecDeque } ;
55use crate :: alloc:: Allocator ;
66#[ cfg( not( test) ) ]
77use crate :: vec;
@@ -157,7 +157,8 @@ impl<T, A: Allocator> SpecExtendFront<T, vec::IntoIter<T>> for VecDeque<T, A> {
157157 #[ track_caller]
158158 fn spec_extend_front ( & mut self , mut iterator : vec:: IntoIter < T > ) {
159159 let slice = iterator. as_slice ( ) ;
160- // SAFETY: elements in the slice are forgotten after this call
160+ self . reserve ( slice. len ( ) ) ;
161+ // SAFETY: `slice.len()` space was just reserved and elements in the slice are forgotten after this call
161162 unsafe { prepend_reversed ( self , slice) } ;
162163 iterator. forget_remaining_elements ( ) ;
163164 }
@@ -169,7 +170,8 @@ impl<T, A: Allocator> SpecExtendFront<T, Rev<vec::IntoIter<T>>> for VecDeque<T,
169170 fn spec_extend_front ( & mut self , iterator : Rev < vec:: IntoIter < T > > ) {
170171 let mut iterator = iterator. into_inner ( ) ;
171172 let slice = iterator. as_slice ( ) ;
172- // SAFETY: elements in the slice are forgotten after this call
173+ self . reserve ( slice. len ( ) ) ;
174+ // SAFETY: `slice.len()` space was just reserved and elements in the slice are forgotten after this call
173175 unsafe { prepend ( self , slice) } ;
174176 iterator. forget_remaining_elements ( ) ;
175177 }
@@ -182,7 +184,8 @@ where
182184 #[ track_caller]
183185 fn spec_extend_front ( & mut self , iter : Copied < slice:: Iter < ' a , T > > ) {
184186 let slice = iter. into_inner ( ) . as_slice ( ) ;
185- // SAFETY: T is Copy because Copied<slice::Iter<'a, T>> is Iterator
187+ self . reserve ( slice. len ( ) ) ;
188+ // SAFETY: `slice.len()` space was just reserved and T is Copy because Copied<slice::Iter<'a, T>> is Iterator
186189 unsafe { prepend_reversed ( self , slice) } ;
187190 }
188191}
@@ -194,30 +197,83 @@ where
194197 #[ track_caller]
195198 fn spec_extend_front ( & mut self , iter : Rev < Copied < slice:: Iter < ' a , T > > > ) {
196199 let slice = iter. into_inner ( ) . into_inner ( ) . as_slice ( ) ;
197- // SAFETY: T is Copy because Rev<Copied<slice::Iter<'a, T>>> is Iterator
200+ self . reserve ( slice. len ( ) ) ;
201+ // SAFETY: `slice.len()` space was just reserved and T is Copy because Rev<Copied<slice::Iter<'a, T>>> is Iterator
198202 unsafe { prepend ( self , slice) } ;
199203 }
200204}
201205
206+ impl < ' a , T , A1 : Allocator , A2 : Allocator > SpecExtendFront < T , Drain < ' a , T , A2 > > for VecDeque < T , A1 > {
207+ #[ track_caller]
208+ fn spec_extend_front ( & mut self , mut iter : Drain < ' a , T , A2 > ) {
209+ if iter. remaining == 0 {
210+ return ;
211+ }
212+
213+ self . reserve ( iter. remaining ) ;
214+ unsafe {
215+ // SAFETY: iter.remaining != 0.
216+ let ( left, right) = iter. as_slices ( ) ;
217+ // SAFETY:
218+ // - `iter.remaining` space was reserved, `iter.remaining == left.len() + right.len()`.
219+ // - The elements in `left` and `right` are forgotten after these calls.
220+ prepend_reversed ( self , & * left) ;
221+ prepend_reversed ( self , & * right) ;
222+ }
223+
224+ iter. idx += iter. remaining ;
225+ iter. remaining = 0 ;
226+ }
227+ }
228+
229+ impl < ' a , T , A1 : Allocator , A2 : Allocator > SpecExtendFront < T , Rev < Drain < ' a , T , A2 > > >
230+ for VecDeque < T , A1 >
231+ {
232+ #[ track_caller]
233+ fn spec_extend_front ( & mut self , iter : Rev < Drain < ' a , T , A2 > > ) {
234+ let mut iter = iter. into_inner ( ) ;
235+
236+ if iter. remaining == 0 {
237+ return ;
238+ }
239+
240+ self . reserve ( iter. remaining ) ;
241+ unsafe {
242+ // SAFETY: iter.remaining != 0.
243+ let ( left, right) = iter. as_slices ( ) ;
244+ // SAFETY:
245+ // - `iter.remaining` space was reserved, `iter.remaining == left.len() + right.len()`.
246+ // - The elements in `left` and `right` are forgotten after these calls.
247+ prepend ( self , & * right) ;
248+ prepend ( self , & * left) ;
249+ }
250+
251+ iter. idx += iter. remaining ;
252+ iter. remaining = 0 ;
253+ }
254+ }
255+
256+ /// Prepends elements of `slice` to `deque` using a copy.
257+ ///
202258/// # Safety
203259///
204- /// Elements of `slice` will be copied into the deque, make sure to forget the items if `T` is not `Copy`.
260+ /// - `deque` must have space for `slice.len()` new elements.
261+ /// - Elements of `slice` will be copied into the deque, make sure to forget the elements if `T` is not `Copy`.
205262unsafe fn prepend < T , A : Allocator > ( deque : & mut VecDeque < T , A > , slice : & [ T ] ) {
206- deque. reserve ( slice. len ( ) ) ;
207-
208263 unsafe {
209264 deque. head = deque. wrap_sub ( deque. head , slice. len ( ) ) ;
210265 deque. copy_slice ( deque. head , slice) ;
211266 deque. len += slice. len ( ) ;
212267 }
213268}
214269
270+ /// Prepends elements of `slice` to `deque` in reverse order using a copy.
271+ ///
215272/// # Safety
216273///
217- /// Elements of `slice` will be copied into the deque, make sure to forget the items if `T` is not `Copy`.
274+ /// - `deque` must have space for `slice.len()` new elements.
275+ /// - Elements of `slice` will be copied into the deque, make sure to forget the elements if `T` is not `Copy`.
218276unsafe fn prepend_reversed < T , A : Allocator > ( deque : & mut VecDeque < T , A > , slice : & [ T ] ) {
219- deque. reserve ( slice. len ( ) ) ;
220-
221277 unsafe {
222278 deque. head = deque. wrap_sub ( deque. head , slice. len ( ) ) ;
223279 deque. copy_slice_reversed ( deque. head , slice) ;
0 commit comments