@@ -964,20 +964,6 @@ impl<T, const N: usize> SmallVec<T, N> {
964
964
unsafe { self . set_len ( len + 1 ) }
965
965
}
966
966
967
- #[ inline]
968
- unsafe fn push_heap ( & mut self , value : T ) {
969
- // SAFETY: see above
970
- debug_assert ! ( self . spilled( ) ) ;
971
- let len = self . len ( ) ;
972
- let cap = self . raw . heap . 1 ;
973
- if len == cap {
974
- self . reserve ( 1 ) ;
975
- }
976
- let ptr = self . raw . heap . 0 ;
977
- ptr. as_ptr ( ) . add ( len) . write ( value) ;
978
- self . set_len ( len + 1 )
979
- }
980
-
981
967
#[ inline]
982
968
pub fn pop ( & mut self ) -> Option < T > {
983
969
if self . is_empty ( ) {
@@ -1502,39 +1488,33 @@ impl<T, const N: usize> SmallVec<T, N> {
1502
1488
1503
1489
fn extend_impl < I : Iterator < Item = T > > ( & mut self , iter : I ) {
1504
1490
let mut iter = iter. fuse ( ) ;
1505
- let len = self . len ( ) ;
1506
1491
let ( lower_bound, _) = iter. size_hint ( ) ;
1507
1492
self . reserve ( lower_bound) ;
1508
- let capacity = self . capacity ( ) ;
1509
- unsafe {
1510
- let ptr = self . as_mut_ptr ( ) ;
1511
- // SAFETY: ptr is valid for `capacity - len` writes
1512
- let count = extend_batch ( ptr, capacity - len, len, & mut iter) ;
1513
- self . set_len ( len + count) ;
1514
- }
1515
-
1516
- if let Some ( item) = iter. next ( ) {
1517
- self . push ( item) ;
1518
- } else {
1519
- return ;
1520
- }
1521
-
1522
- // either we ran out of items, in which case this loop doesn't get executed. or we still
1523
- // have items to push, and in that case we must be on the heap, since we filled up the
1524
- // capacity and then pushed one item
1493
+ let mut len = self . len ( ) ;
1494
+ let mut capacity = self . capacity ( ) ;
1495
+ let mut ptr = self . as_mut_ptr ( ) ;
1525
1496
unsafe {
1526
1497
loop {
1498
+ // SAFETY: ptr is valid for `capacity - len` writes
1499
+ ptr = ptr. add ( len) ;
1500
+ let mut guard = DropGuard { ptr, len : 0 } ;
1501
+ iter. by_ref ( ) . take ( capacity - len) . for_each ( |item| {
1502
+ ptr. add ( guard. len ) . write ( item) ;
1503
+ guard. len += 1 ;
1504
+ } ) ;
1505
+ len += guard. len ;
1506
+ core:: mem:: forget ( guard) ;
1507
+ self . set_len ( len) ;
1508
+ // At this point we either consumed all capacity or the iterator is exhausted (fused)
1527
1509
if let Some ( item) = iter. next ( ) {
1528
- self . push_heap ( item) ;
1510
+ self . push ( item) ;
1529
1511
} else {
1530
- break ;
1512
+ return ;
1531
1513
}
1532
- let len = self . len ( ) ;
1533
- let ( ptr, capacity) = self . raw . heap ;
1534
- let ptr = ptr. as_ptr ( ) ;
1535
- // SAFETY: ptr is valid for `capacity - len` writes
1536
- let count = extend_batch ( ptr, capacity - len, len, & mut iter) ;
1537
- self . set_len ( len + count) ;
1514
+ // SAFETY: The push above would have spilled it
1515
+ let ( heap_ptr, heap_capacity) = self . raw . heap ;
1516
+ ptr = heap_ptr. as_ptr ( ) ;
1517
+ capacity = heap_capacity;
1538
1518
}
1539
1519
}
1540
1520
}
@@ -1703,30 +1683,6 @@ unsafe fn insert_many_batch<T, I: Iterator<Item = T>>(
1703
1683
count
1704
1684
}
1705
1685
1706
- // `ptr..ptr + remaining_capacity` must be valid for writes
1707
- #[ inline]
1708
- unsafe fn extend_batch < T , I : Iterator < Item = T > > (
1709
- ptr : * mut T ,
1710
- remaining_capacity : usize ,
1711
- len : usize ,
1712
- iter : & mut I ,
1713
- ) -> usize {
1714
- let ptr_end = ptr. add ( len) ;
1715
- let mut guard = DropGuard {
1716
- ptr : ptr_end,
1717
- len : 0 ,
1718
- } ;
1719
- iter. take ( remaining_capacity)
1720
- . enumerate ( )
1721
- . for_each ( |( i, item) | {
1722
- ptr_end. add ( i) . write ( item) ;
1723
- guard. len = i + 1 ;
1724
- } ) ;
1725
- let count = guard. len ;
1726
- core:: mem:: forget ( guard) ;
1727
- count
1728
- }
1729
-
1730
1686
impl < T , const N : usize > Extend < T > for SmallVec < T , N > {
1731
1687
#[ inline]
1732
1688
fn extend < I : IntoIterator < Item = T > > ( & mut self , iterable : I ) {
0 commit comments