Skip to content

Commit 43732a2

Browse files
Use internal iteration in Vec::extend_desugared()
Because LLVM is unable to optimize well external iteration with some iterator kinds (e.g. `chain()`).
1 parent a1208bf commit 43732a2

File tree

1 file changed

+8
-13
lines changed

1 file changed

+8
-13
lines changed

library/alloc/src/vec/mod.rs

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -3788,19 +3788,14 @@ impl<T, A: Allocator> Vec<T, A> {
37883788
// for item in iterator {
37893789
// self.push(item);
37903790
// }
3791-
while let Some(element) = iterator.next() {
3792-
let len = self.len();
3793-
if len == self.capacity() {
3794-
let (lower, _) = iterator.size_hint();
3795-
self.reserve(lower.saturating_add(1));
3796-
}
3797-
unsafe {
3798-
ptr::write(self.as_mut_ptr().add(len), element);
3799-
// Since next() executes user code which can panic we have to bump the length
3800-
// after each step.
3801-
// NB can't overflow since we would have had to alloc the address space
3802-
self.set_len(len + 1);
3803-
}
3791+
while let Err(item) = iterator.try_for_each(|item| self.push_within_capacity(item)) {
3792+
// As long as there is enough space, we push the items directly into
3793+
// the vector. Once we need more space, look at the iterators size
3794+
// hint to get an estimate for how much space to reserve.
3795+
let (lower, _) = iterator.size_hint();
3796+
self.reserve(lower.saturating_add(1));
3797+
// SAFETY: we just reserved space for at least one item.
3798+
unsafe { self.push_within_capacity(item).unwrap_unchecked() };
38043799
}
38053800
}
38063801

0 commit comments

Comments
 (0)