Skip to content

Commit d5c05fc

Browse files
authored
Rollup merge of rust-lang#93057 - frengor:iter_collect_into, r=m-ou-se
Add Iterator::collect_into This PR adds `Iterator::collect_into` as proposed by ``@cormacrelf`` in rust-lang#48597 (see rust-lang#48597 (comment)). Followup of rust-lang#92982. This adds the following method to the Iterator trait: ```rust fn collect_into<E: Extend<Self::Item>>(self, collection: &mut E) -> &mut E ```
2 parents 2567d0f + 63eddb3 commit d5c05fc

File tree

3 files changed

+80
-0
lines changed

3 files changed

+80
-0
lines changed

library/core/src/iter/traits/iterator.rs

+71
Original file line numberDiff line numberDiff line change
@@ -1859,6 +1859,77 @@ pub trait Iterator {
18591859
try_process(self, |i| i.collect())
18601860
}
18611861

1862+
/// Collects all the items from an iterator into a collection.
1863+
///
1864+
/// This method consumes the iterator and adds all its items to the
1865+
/// passed collection. The collection is then returned, so the call chain
1866+
/// can be continued.
1867+
///
1868+
/// This is useful when you already have a collection and wants to add
1869+
/// the iterator items to it.
1870+
///
1871+
/// This method is a convenience method to call [Extend::extend](trait.Extend.html),
1872+
/// but instead of being called on a collection, it's called on an iterator.
1873+
///
1874+
/// # Examples
1875+
///
1876+
/// Basic usage:
1877+
///
1878+
/// ```
1879+
/// #![feature(iter_collect_into)]
1880+
///
1881+
/// let a = [1, 2, 3];
1882+
/// let mut vec: Vec::<i32> = vec![0, 1];
1883+
///
1884+
/// a.iter().map(|&x| x * 2).collect_into(&mut vec);
1885+
/// a.iter().map(|&x| x * 10).collect_into(&mut vec);
1886+
///
1887+
/// assert_eq!(vec![0, 1, 2, 4, 6, 10, 20, 30], vec);
1888+
/// ```
1889+
///
1890+
/// `Vec` can have a manual set capacity to avoid reallocating it:
1891+
///
1892+
/// ```
1893+
/// #![feature(iter_collect_into)]
1894+
///
1895+
/// let a = [1, 2, 3];
1896+
/// let mut vec: Vec::<i32> = Vec::with_capacity(6);
1897+
///
1898+
/// a.iter().map(|&x| x * 2).collect_into(&mut vec);
1899+
/// a.iter().map(|&x| x * 10).collect_into(&mut vec);
1900+
///
1901+
/// assert_eq!(6, vec.capacity());
1902+
/// println!("{:?}", vec);
1903+
/// ```
1904+
///
1905+
/// The returned mutable reference can be used to continue the call chain:
1906+
///
1907+
/// ```
1908+
/// #![feature(iter_collect_into)]
1909+
///
1910+
/// let a = [1, 2, 3];
1911+
/// let mut vec: Vec::<i32> = Vec::with_capacity(6);
1912+
///
1913+
/// let count = a.iter().collect_into(&mut vec).iter().count();
1914+
///
1915+
/// assert_eq!(count, vec.len());
1916+
/// println!("Vec len is {}", count);
1917+
///
1918+
/// let count = a.iter().collect_into(&mut vec).iter().count();
1919+
///
1920+
/// assert_eq!(count, vec.len());
1921+
/// println!("Vec len now is {}", count);
1922+
/// ```
1923+
#[inline]
1924+
#[unstable(feature = "iter_collect_into", reason = "new API", issue = "94780")]
1925+
fn collect_into<E: Extend<Self::Item>>(self, collection: &mut E) -> &mut E
1926+
where
1927+
Self: Sized,
1928+
{
1929+
collection.extend(self);
1930+
collection
1931+
}
1932+
18621933
/// Consumes an iterator, creating two collections from it.
18631934
///
18641935
/// The predicate passed to `partition()` can return `true`, or `false`.

library/core/tests/iter/traits/iterator.rs

+8
Original file line numberDiff line numberDiff line change
@@ -543,6 +543,14 @@ fn test_try_collect() {
543543
assert_eq!(v, Continue(vec![4, 5]));
544544
}
545545

546+
#[test]
547+
fn test_collect_into() {
548+
let a = vec![1, 2, 3, 4, 5];
549+
let mut b = Vec::new();
550+
a.iter().cloned().collect_into(&mut b);
551+
assert!(a == b);
552+
}
553+
546554
// just tests by whether or not this compiles
547555
fn _empty_impl_all_auto_traits<T>() {
548556
use std::panic::{RefUnwindSafe, UnwindSafe};

library/core/tests/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@
6262
#![feature(slice_partition_dedup)]
6363
#![feature(int_log)]
6464
#![feature(iter_advance_by)]
65+
#![feature(iter_collect_into)]
6566
#![feature(iter_partition_in_place)]
6667
#![feature(iter_intersperse)]
6768
#![feature(iter_is_partitioned)]

0 commit comments

Comments
 (0)