You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
IntoIterator should be implemented for [T; N] not just references #25725
Currently IntoIterator is implemented for arrays of &'a mut [T; N] and &'a [T; N] but not for [T; N] making it only possible to collect() arrays of references, not arrays of values:
// These are the same in spite of `iter()` changing to `into_iter()`.let vec_ref1:Vec<&i32> = [1,2].iter().collect();let vec_ref2:Vec<&i32> = [1,2].into_iter().collect();// This is what `into_iter()` should do but it doesn't actually work.let vec:Vec<i32> = [1,2].into_iter().collect();
This is something users are likely to run headlong into (probably accidentally) when testing out examples from the iterator docs. So, IntoIterator should be implemented so that last option is possible. The API stabilization RFC: rust-lang/rfcs#1105 states:
any breakage in a minor release ... it must always be possible to locally fix the problem through some kind of disambiguation that could have been done in advance
Meaning this would be allowed as a minor change in spite of [1, 2].into_iter() behavior changing because it could be changed beforehand to [1, 2].iter().
Reacted by mitchmindtree, Lukas Kalbertodt, chpio, Denis Kolodin, Jonas Schievink, Daniel Hauser, Milo, Leonardo Yvens, Rolf Karp, Cameron Steffen and 83 more
This is tricky to implement for an arbitrary T as panics need to be handled where a moved-out element isn't dropped, and this also leads to a large number of iterators where the reference-based IntoIterator implementations just return a normal slice iterator.
For the record, crate arrayvec implements a by-value iterator using one type and a trait for a range of array sizes. I think it has solved all safety concerns, but I'll definitely look into what happens during panic again.
I take it this would/will be much easier once rust-lang/rfcs#1038 is implemented someday. Then at a minimum, this would be fixable shortly after that issue is.
The lack of this shows up in the beginnings of the book, and it's really annoying. I've shown off arrays, I've shown off loops, I want to show for over arrays. But I haven't introduced method syntax yet, so for e in a.iter() is something new. But you won't often be calling iter() explicitly when you're using Vecs, but we haven't introduced Vec yet either.
Reacted by mitchmindtree, Lukas Kalbertodt, Henning Ottesen, ShikChen and Jacques Rimbault
Just thought I'd give this a +1 and add that I come across this quite frequently. I even occasionally resort to once(a).chain(once(b)).chain(once(c)) during some calls to flat_map just so I can remain on the stack when the only other alternatives are vec![a, b, c] or having to import another crate like arrayvec.
This is tricky to implement for an arbitrary T as panics need to be handled where a moved-out element isn't dropped
At least 90% of my use cases for this are for arrays where the elements are Copy, which I think avoids this issue as a type cannot impl both Copy and Drop. Perhaps it could be useful to first provide an IntoIterator implementation that requires the Copy bound, which may be removed later down the track if we're able to come up with a solution for non-Copy types? Alternatively, perhaps a .copy_iter() that takes self where T: Copy might be useful until a more generalised .into_iter() can be implemented?
Edit: I just want to add that often, .iter().cloned() is not a possible solution when your array has a very short lifetime, i.e.
let(r, g, b) = rgb();let rgbas:Vec<_> = alphas.into_iter().flat_map(|a| [r, g, b, a].iter().cloned())// This fails due to an insufficient lifetime// .flat_map(|a| [r, g, b, a]) // This would be sooo nice.collect();
Reacted by bluss, chpio, Benjamin Saunders, Johan Gardell, Colin Stearns, André Vicente Milack, cynecx, Oleh Misarosh, Matt Keeter, Vladimir Feinberg and 4 more
+1, I also ran against this problem yesterday with this snippet (the Vec variant compiles, array does not). This is very surprising, especially for a beginner.
Get Const generics rfcs#2000 merged + implemented first (assuming stable code can use it without stabilizing const-generic, otherwise we need to count in stabilization time as well)
FYI: an by-value iterator for arrays was implemented in #62959. It is still unstable and missing the actual IntoIterator impl for arrays. That impl will (maybe) be added in #65819, but some discussion regarding backwards compatibility is necessary first. In case you want to chime in.
Reacted by Thomas B and Denis Kolodin
Reacted by Osspial, José Manuel Barroso Galindo, Jenan Wise, Matt Keeter, Ryan Boehning, Iago-lito, Denis Kolodin and Yujin
Activity
mdinger commentedon May 22, 2015
cc @bluss
alexcrichton commentedon May 26, 2015
This is tricky to implement for an arbitrary
Tas panics need to be handled where a moved-out element isn't dropped, and this also leads to a large number of iterators where the reference-basedIntoIteratorimplementations just return a normal slice iterator.bluss commentedon May 26, 2015
For the record, crate arrayvec implements a by-value iterator using one type and a trait for a range of array sizes. I think it has solved all safety concerns, but I'll definitely look into what happens during panic again.
mdinger commentedon May 27, 2015
I take it this would/will be much easier once rust-lang/rfcs#1038 is implemented someday. Then at a minimum, this would be fixable shortly after that issue is.
steveklabnik commentedon Dec 21, 2015
The lack of this shows up in the beginnings of the book, and it's really annoying. I've shown off arrays, I've shown off loops, I want to show for over arrays. But I haven't introduced method syntax yet, so
for e in a.iter()is something new. But you won't often be callingiter()explicitly when you're usingVecs, but we haven't introducedVecyet either.mitchmindtree commentedon Jul 22, 2016
Just thought I'd give this a +1 and add that I come across this quite frequently. I even occasionally resort to
once(a).chain(once(b)).chain(once(c))during some calls toflat_mapjust so I can remain on the stack when the only other alternatives arevec![a, b, c]or having to import another crate like arrayvec.At least 90% of my use cases for this are for arrays where the elements are
Copy, which I think avoids this issue as a type cannotimplbothCopyandDrop. Perhaps it could be useful to first provide anIntoIteratorimplementation that requires theCopybound, which may be removed later down the track if we're able to come up with a solution for non-Copytypes? Alternatively, perhaps a.copy_iter()that takesselfwhereT: Copymight be useful until a more generalised.into_iter()can be implemented?Edit: I just want to add that often,
.iter().cloned()is not a possible solution when your array has a very short lifetime, i.e.haudan commentedon Aug 10, 2017
+1, I also ran against this problem yesterday with this snippet (the Vec variant compiles, array does not). This is very surprising, especially for a beginner.
kennytm commentedon Aug 10, 2017
As discussed in #32871, we either need:
impl Traitto be stable, so we could secretly use theimpl IntoIterator for [T; 0]to[T; 32]trick (probably also need Named existentials and impl Trait variable declarations rfcs#2071 to name the associated type), orAuto merge of #49000 - cuviper:array-intoiter, r=<try>
28 remaining items
Rollup merge of rust-lang#62959 - LukasKalbertodt:array-value-iter, r…
LukasKalbertodt commentedon Oct 25, 2019
FYI: an by-value iterator for arrays was implemented in #62959. It is still unstable and missing the actual
IntoIteratorimpl for arrays. That impl will (maybe) be added in #65819, but some discussion regarding backwards compatibility is necessary first. In case you want to chime in.m-ou-se commentedon Apr 26, 2021
This trait implementation has now been added, with a small hack to avoid changing the meaning of
array.into_iter()until Rust 2021: #84147Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis
Rollup merge of rust-lang#84590 - est31:array_into_iter, r=nikomatsakis