mirror of
https://github.com/rust-lang/rust-analyzer
synced 2025-01-14 06:03:58 +00:00
fix(todo): implement IntoIterator for ArenaMap<IDX, V>
This commit is contained in:
parent
a4966c9282
commit
c5e0607915
1 changed files with 58 additions and 6 deletions
|
@ -1,3 +1,4 @@
|
|||
use std::iter::Enumerate;
|
||||
use std::marker::PhantomData;
|
||||
|
||||
use crate::Idx;
|
||||
|
@ -94,12 +95,6 @@ impl<T, V> ArenaMap<Idx<T>, V> {
|
|||
.filter_map(|(idx, o)| Some((Self::from_idx(idx), o.as_mut()?)))
|
||||
}
|
||||
|
||||
/// Returns an iterator over the arena indexes and values in the map.
|
||||
// FIXME: Implement `IntoIterator` trait.
|
||||
pub fn into_iter(self) -> impl Iterator<Item = (Idx<T>, V)> + DoubleEndedIterator {
|
||||
self.v.into_iter().enumerate().filter_map(|(idx, o)| Some((Self::from_idx(idx), o?)))
|
||||
}
|
||||
|
||||
/// Gets the given key's corresponding entry in the map for in-place manipulation.
|
||||
pub fn entry(&mut self, idx: Idx<T>) -> Entry<'_, Idx<T>, V> {
|
||||
let idx = Self::to_idx(idx);
|
||||
|
@ -154,6 +149,63 @@ impl<T, V> FromIterator<(Idx<V>, T)> for ArenaMap<Idx<V>, T> {
|
|||
}
|
||||
}
|
||||
|
||||
pub struct ArenaMapIter<IDX, V> {
|
||||
iter: Enumerate<std::vec::IntoIter<Option<V>>>,
|
||||
_ty: PhantomData<IDX>,
|
||||
}
|
||||
|
||||
impl<T, V> IntoIterator for ArenaMap<Idx<T>, V> {
|
||||
type Item = (Idx<T>, V);
|
||||
|
||||
type IntoIter = ArenaMapIter<Idx<T>, V>;
|
||||
|
||||
fn into_iter(self) -> Self::IntoIter {
|
||||
let iter = self.v.into_iter().enumerate();
|
||||
Self::IntoIter { iter, _ty: PhantomData }
|
||||
}
|
||||
}
|
||||
|
||||
impl<T, V> ArenaMapIter<Idx<T>, V> {
|
||||
fn mapper((idx, o): (usize, Option<V>)) -> Option<(Idx<T>, V)> {
|
||||
Some((ArenaMap::<Idx<T>, V>::from_idx(idx), o?))
|
||||
}
|
||||
}
|
||||
|
||||
impl<T, V> Iterator for ArenaMapIter<Idx<T>, V> {
|
||||
type Item = (Idx<T>, V);
|
||||
|
||||
#[inline]
|
||||
fn next(&mut self) -> Option<Self::Item> {
|
||||
for next in self.iter.by_ref() {
|
||||
match Self::mapper(next) {
|
||||
Some(r) => return Some(r),
|
||||
None => continue,
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn size_hint(&self) -> (usize, Option<usize>) {
|
||||
self.iter.size_hint()
|
||||
}
|
||||
}
|
||||
|
||||
impl<T, V> DoubleEndedIterator for ArenaMapIter<Idx<T>, V> {
|
||||
#[inline]
|
||||
fn next_back(&mut self) -> Option<Self::Item> {
|
||||
while let Some(next_back) = self.iter.next_back() {
|
||||
match Self::mapper(next_back) {
|
||||
Some(r) => return Some(r),
|
||||
None => continue,
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
/// A view into a single entry in a map, which may either be vacant or occupied.
|
||||
///
|
||||
/// This `enum` is constructed from the [`entry`] method on [`ArenaMap`].
|
||||
|
|
Loading…
Reference in a new issue