Skip to content

Commit dbb37fb

Browse files
authored
Rollup merge of #78590 - DeveloperC286:issue_60302, r=varkor
refactor: removing alloc::collections::vec_deque ignore-tidy-filelength This PR removes the need for ignore-tidy-filelength for alloc::collections::vec_deque which is part of the issue #60302 It is probably easiest to review this PR by looking at it commit by commit rather than looking at the overall diff.
2 parents dc4d655 + 75dfc71 commit dbb37fb

File tree

8 files changed

+515
-473
lines changed

8 files changed

+515
-473
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
use core::fmt;
2+
use core::iter::FusedIterator;
3+
4+
use super::VecDeque;
5+
6+
/// An owning iterator over the elements of a `VecDeque`.
7+
///
8+
/// This `struct` is created by the [`into_iter`] method on [`VecDeque`]
9+
/// (provided by the `IntoIterator` trait). See its documentation for more.
10+
///
11+
/// [`into_iter`]: VecDeque::into_iter
12+
#[derive(Clone)]
13+
#[stable(feature = "rust1", since = "1.0.0")]
14+
pub struct IntoIter<T> {
15+
pub(crate) inner: VecDeque<T>,
16+
}
17+
18+
#[stable(feature = "collection_debug", since = "1.17.0")]
19+
impl<T: fmt::Debug> fmt::Debug for IntoIter<T> {
20+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
21+
f.debug_tuple("IntoIter").field(&self.inner).finish()
22+
}
23+
}
24+
25+
#[stable(feature = "rust1", since = "1.0.0")]
26+
impl<T> Iterator for IntoIter<T> {
27+
type Item = T;
28+
29+
#[inline]
30+
fn next(&mut self) -> Option<T> {
31+
self.inner.pop_front()
32+
}
33+
34+
#[inline]
35+
fn size_hint(&self) -> (usize, Option<usize>) {
36+
let len = self.inner.len();
37+
(len, Some(len))
38+
}
39+
}
40+
41+
#[stable(feature = "rust1", since = "1.0.0")]
42+
impl<T> DoubleEndedIterator for IntoIter<T> {
43+
#[inline]
44+
fn next_back(&mut self) -> Option<T> {
45+
self.inner.pop_back()
46+
}
47+
}
48+
49+
#[stable(feature = "rust1", since = "1.0.0")]
50+
impl<T> ExactSizeIterator for IntoIter<T> {
51+
fn is_empty(&self) -> bool {
52+
self.inner.is_empty()
53+
}
54+
}
55+
56+
#[stable(feature = "fused", since = "1.26.0")]
57+
impl<T> FusedIterator for IntoIter<T> {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,159 @@
1+
use core::fmt;
2+
use core::iter::FusedIterator;
3+
use core::ops::Try;
4+
5+
use super::{count, wrap_index, RingSlices};
6+
7+
/// An iterator over the elements of a `VecDeque`.
8+
///
9+
/// This `struct` is created by the [`iter`] method on [`super::VecDeque`]. See its
10+
/// documentation for more.
11+
///
12+
/// [`iter`]: super::VecDeque::iter
13+
#[stable(feature = "rust1", since = "1.0.0")]
14+
pub struct Iter<'a, T: 'a> {
15+
pub(crate) ring: &'a [T],
16+
pub(crate) tail: usize,
17+
pub(crate) head: usize,
18+
}
19+
20+
#[stable(feature = "collection_debug", since = "1.17.0")]
21+
impl<T: fmt::Debug> fmt::Debug for Iter<'_, T> {
22+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
23+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
24+
f.debug_tuple("Iter").field(&front).field(&back).finish()
25+
}
26+
}
27+
28+
// FIXME(#26925) Remove in favor of `#[derive(Clone)]`
29+
#[stable(feature = "rust1", since = "1.0.0")]
30+
impl<T> Clone for Iter<'_, T> {
31+
fn clone(&self) -> Self {
32+
Iter { ring: self.ring, tail: self.tail, head: self.head }
33+
}
34+
}
35+
36+
#[stable(feature = "rust1", since = "1.0.0")]
37+
impl<'a, T> Iterator for Iter<'a, T> {
38+
type Item = &'a T;
39+
40+
#[inline]
41+
fn next(&mut self) -> Option<&'a T> {
42+
if self.tail == self.head {
43+
return None;
44+
}
45+
let tail = self.tail;
46+
self.tail = wrap_index(self.tail.wrapping_add(1), self.ring.len());
47+
unsafe { Some(self.ring.get_unchecked(tail)) }
48+
}
49+
50+
#[inline]
51+
fn size_hint(&self) -> (usize, Option<usize>) {
52+
let len = count(self.tail, self.head, self.ring.len());
53+
(len, Some(len))
54+
}
55+
56+
fn fold<Acc, F>(self, mut accum: Acc, mut f: F) -> Acc
57+
where
58+
F: FnMut(Acc, Self::Item) -> Acc,
59+
{
60+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
61+
accum = front.iter().fold(accum, &mut f);
62+
back.iter().fold(accum, &mut f)
63+
}
64+
65+
fn try_fold<B, F, R>(&mut self, init: B, mut f: F) -> R
66+
where
67+
Self: Sized,
68+
F: FnMut(B, Self::Item) -> R,
69+
R: Try<Ok = B>,
70+
{
71+
let (mut iter, final_res);
72+
if self.tail <= self.head {
73+
// single slice self.ring[self.tail..self.head]
74+
iter = self.ring[self.tail..self.head].iter();
75+
final_res = iter.try_fold(init, &mut f);
76+
} else {
77+
// two slices: self.ring[self.tail..], self.ring[..self.head]
78+
let (front, back) = self.ring.split_at(self.tail);
79+
let mut back_iter = back.iter();
80+
let res = back_iter.try_fold(init, &mut f);
81+
let len = self.ring.len();
82+
self.tail = (self.ring.len() - back_iter.len()) & (len - 1);
83+
iter = front[..self.head].iter();
84+
final_res = iter.try_fold(res?, &mut f);
85+
}
86+
self.tail = self.head - iter.len();
87+
final_res
88+
}
89+
90+
fn nth(&mut self, n: usize) -> Option<Self::Item> {
91+
if n >= count(self.tail, self.head, self.ring.len()) {
92+
self.tail = self.head;
93+
None
94+
} else {
95+
self.tail = wrap_index(self.tail.wrapping_add(n), self.ring.len());
96+
self.next()
97+
}
98+
}
99+
100+
#[inline]
101+
fn last(mut self) -> Option<&'a T> {
102+
self.next_back()
103+
}
104+
}
105+
106+
#[stable(feature = "rust1", since = "1.0.0")]
107+
impl<'a, T> DoubleEndedIterator for Iter<'a, T> {
108+
#[inline]
109+
fn next_back(&mut self) -> Option<&'a T> {
110+
if self.tail == self.head {
111+
return None;
112+
}
113+
self.head = wrap_index(self.head.wrapping_sub(1), self.ring.len());
114+
unsafe { Some(self.ring.get_unchecked(self.head)) }
115+
}
116+
117+
fn rfold<Acc, F>(self, mut accum: Acc, mut f: F) -> Acc
118+
where
119+
F: FnMut(Acc, Self::Item) -> Acc,
120+
{
121+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
122+
accum = back.iter().rfold(accum, &mut f);
123+
front.iter().rfold(accum, &mut f)
124+
}
125+
126+
fn try_rfold<B, F, R>(&mut self, init: B, mut f: F) -> R
127+
where
128+
Self: Sized,
129+
F: FnMut(B, Self::Item) -> R,
130+
R: Try<Ok = B>,
131+
{
132+
let (mut iter, final_res);
133+
if self.tail <= self.head {
134+
// single slice self.ring[self.tail..self.head]
135+
iter = self.ring[self.tail..self.head].iter();
136+
final_res = iter.try_rfold(init, &mut f);
137+
} else {
138+
// two slices: self.ring[self.tail..], self.ring[..self.head]
139+
let (front, back) = self.ring.split_at(self.tail);
140+
let mut front_iter = front[..self.head].iter();
141+
let res = front_iter.try_rfold(init, &mut f);
142+
self.head = front_iter.len();
143+
iter = back.iter();
144+
final_res = iter.try_rfold(res?, &mut f);
145+
}
146+
self.head = self.tail + iter.len();
147+
final_res
148+
}
149+
}
150+
151+
#[stable(feature = "rust1", since = "1.0.0")]
152+
impl<T> ExactSizeIterator for Iter<'_, T> {
153+
fn is_empty(&self) -> bool {
154+
self.head == self.tail
155+
}
156+
}
157+
158+
#[stable(feature = "fused", since = "1.26.0")]
159+
impl<T> FusedIterator for Iter<'_, T> {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,128 @@
1+
use core::fmt;
2+
use core::iter::FusedIterator;
3+
use core::marker::PhantomData;
4+
5+
use super::{count, wrap_index, RingSlices};
6+
7+
/// A mutable iterator over the elements of a `VecDeque`.
8+
///
9+
/// This `struct` is created by the [`iter_mut`] method on [`super::VecDeque`]. See its
10+
/// documentation for more.
11+
///
12+
/// [`iter_mut`]: super::VecDeque::iter_mut
13+
#[stable(feature = "rust1", since = "1.0.0")]
14+
pub struct IterMut<'a, T: 'a> {
15+
// Internal safety invariant: the entire slice is dereferencable.
16+
pub(crate) ring: *mut [T],
17+
pub(crate) tail: usize,
18+
pub(crate) head: usize,
19+
pub(crate) phantom: PhantomData<&'a mut [T]>,
20+
}
21+
22+
// SAFETY: we do nothing thread-local and there is no interior mutability,
23+
// so the usual structural `Send`/`Sync` apply.
24+
#[stable(feature = "rust1", since = "1.0.0")]
25+
unsafe impl<T: Send> Send for IterMut<'_, T> {}
26+
#[stable(feature = "rust1", since = "1.0.0")]
27+
unsafe impl<T: Sync> Sync for IterMut<'_, T> {}
28+
29+
#[stable(feature = "collection_debug", since = "1.17.0")]
30+
impl<T: fmt::Debug> fmt::Debug for IterMut<'_, T> {
31+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
32+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
33+
// SAFETY: these are the elements we have not handed out yet, so aliasing is fine.
34+
// The `IterMut` invariant also ensures everything is dereferencable.
35+
let (front, back) = unsafe { (&*front, &*back) };
36+
f.debug_tuple("IterMut").field(&front).field(&back).finish()
37+
}
38+
}
39+
40+
#[stable(feature = "rust1", since = "1.0.0")]
41+
impl<'a, T> Iterator for IterMut<'a, T> {
42+
type Item = &'a mut T;
43+
44+
#[inline]
45+
fn next(&mut self) -> Option<&'a mut T> {
46+
if self.tail == self.head {
47+
return None;
48+
}
49+
let tail = self.tail;
50+
self.tail = wrap_index(self.tail.wrapping_add(1), self.ring.len());
51+
52+
unsafe {
53+
let elem = self.ring.get_unchecked_mut(tail);
54+
Some(&mut *elem)
55+
}
56+
}
57+
58+
#[inline]
59+
fn size_hint(&self) -> (usize, Option<usize>) {
60+
let len = count(self.tail, self.head, self.ring.len());
61+
(len, Some(len))
62+
}
63+
64+
fn fold<Acc, F>(self, mut accum: Acc, mut f: F) -> Acc
65+
where
66+
F: FnMut(Acc, Self::Item) -> Acc,
67+
{
68+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
69+
// SAFETY: these are the elements we have not handed out yet, so aliasing is fine.
70+
// The `IterMut` invariant also ensures everything is dereferencable.
71+
let (front, back) = unsafe { (&mut *front, &mut *back) };
72+
accum = front.iter_mut().fold(accum, &mut f);
73+
back.iter_mut().fold(accum, &mut f)
74+
}
75+
76+
fn nth(&mut self, n: usize) -> Option<Self::Item> {
77+
if n >= count(self.tail, self.head, self.ring.len()) {
78+
self.tail = self.head;
79+
None
80+
} else {
81+
self.tail = wrap_index(self.tail.wrapping_add(n), self.ring.len());
82+
self.next()
83+
}
84+
}
85+
86+
#[inline]
87+
fn last(mut self) -> Option<&'a mut T> {
88+
self.next_back()
89+
}
90+
}
91+
92+
#[stable(feature = "rust1", since = "1.0.0")]
93+
impl<'a, T> DoubleEndedIterator for IterMut<'a, T> {
94+
#[inline]
95+
fn next_back(&mut self) -> Option<&'a mut T> {
96+
if self.tail == self.head {
97+
return None;
98+
}
99+
self.head = wrap_index(self.head.wrapping_sub(1), self.ring.len());
100+
101+
unsafe {
102+
let elem = self.ring.get_unchecked_mut(self.head);
103+
Some(&mut *elem)
104+
}
105+
}
106+
107+
fn rfold<Acc, F>(self, mut accum: Acc, mut f: F) -> Acc
108+
where
109+
F: FnMut(Acc, Self::Item) -> Acc,
110+
{
111+
let (front, back) = RingSlices::ring_slices(self.ring, self.head, self.tail);
112+
// SAFETY: these are the elements we have not handed out yet, so aliasing is fine.
113+
// The `IterMut` invariant also ensures everything is dereferencable.
114+
let (front, back) = unsafe { (&mut *front, &mut *back) };
115+
accum = back.iter_mut().rfold(accum, &mut f);
116+
front.iter_mut().rfold(accum, &mut f)
117+
}
118+
}
119+
120+
#[stable(feature = "rust1", since = "1.0.0")]
121+
impl<T> ExactSizeIterator for IterMut<'_, T> {
122+
fn is_empty(&self) -> bool {
123+
self.head == self.tail
124+
}
125+
}
126+
127+
#[stable(feature = "fused", since = "1.26.0")]
128+
impl<T> FusedIterator for IterMut<'_, T> {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
macro_rules! __impl_slice_eq1 {
2+
([$($vars:tt)*] $lhs:ty, $rhs:ty, $($constraints:tt)*) => {
3+
#[stable(feature = "vec_deque_partial_eq_slice", since = "1.17.0")]
4+
impl<A, B, $($vars)*> PartialEq<$rhs> for $lhs
5+
where
6+
A: PartialEq<B>,
7+
$($constraints)*
8+
{
9+
fn eq(&self, other: &$rhs) -> bool {
10+
if self.len() != other.len() {
11+
return false;
12+
}
13+
let (sa, sb) = self.as_slices();
14+
let (oa, ob) = other[..].split_at(sa.len());
15+
sa == oa && sb == ob
16+
}
17+
}
18+
}
19+
}

0 commit comments

Comments
 (0)