Skip to content

Commit 859c3ba

Browse files
committed
auto merge of #10519 : nikomatsakis/rust/issue-8624-borrowck-overly-permissive, r=pnkfelix
See #8624 for details. r? @pnkfelix
2 parents 42ea44b + 09e12fa commit 859c3ba

File tree

10 files changed

+583
-154
lines changed

10 files changed

+583
-154
lines changed

src/libextra/dlist.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -225,8 +225,9 @@ impl<T> Deque<T> for DList<T> {
225225
/// Provide a mutable reference to the back element, or None if the list is empty
226226
#[inline]
227227
fn back_mut<'a>(&'a mut self) -> Option<&'a mut T> {
228-
let mut tmp = self.list_tail.resolve(); // FIXME: #3511: shouldn't need variable
229-
tmp.as_mut().map(|tail| &mut tail.value)
228+
let tmp: Option<&'a mut Node<T>> =
229+
self.list_tail.resolve(); // FIXME: #3511: shouldn't need variable
230+
tmp.map(|tail| &mut tail.value)
230231
}
231232

232233
/// Add an element first in the list

src/libextra/ringbuf.rs

+108-47
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,28 @@ impl<T> RingBuf<T> {
198198

199199
/// Front-to-back iterator which returns mutable values.
200200
pub fn mut_iter<'a>(&'a mut self) -> RingBufMutIterator<'a, T> {
201-
RingBufMutIterator{index: 0, rindex: self.nelts, lo: self.lo, elts: self.elts}
201+
let start_index = raw_index(self.lo, self.elts.len(), 0);
202+
let end_index = raw_index(self.lo, self.elts.len(), self.nelts);
203+
204+
// Divide up the array
205+
if end_index <= start_index {
206+
// Items to iterate goes from:
207+
// start_index to self.elts.len()
208+
// and then
209+
// 0 to end_index
210+
let (temp, remaining1) = self.elts.mut_split(start_index);
211+
let (remaining2, _) = temp.mut_split(end_index);
212+
RingBufMutIterator { remaining1: remaining1,
213+
remaining2: remaining2,
214+
nelts: self.nelts }
215+
} else {
216+
// Items to iterate goes from start_index to end_index:
217+
let (empty, elts) = self.elts.mut_split(0);
218+
let remaining1 = elts.mut_slice(start_index, end_index);
219+
RingBufMutIterator { remaining1: remaining1,
220+
remaining2: empty,
221+
nelts: self.nelts }
222+
}
202223
}
203224

204225
/// Back-to-front iterator which returns mutable values.
@@ -207,54 +228,43 @@ impl<T> RingBuf<T> {
207228
}
208229
}
209230

210-
macro_rules! iterator {
211-
(impl $name:ident -> $elem:ty, $getter:ident) => {
212-
impl<'self, T> Iterator<$elem> for $name<'self, T> {
213-
#[inline]
214-
fn next(&mut self) -> Option<$elem> {
215-
if self.index == self.rindex {
216-
return None;
217-
}
218-
let raw_index = raw_index(self.lo, self.elts.len(), self.index);
219-
self.index += 1;
220-
Some(self.elts[raw_index] . $getter ())
221-
}
231+
/// RingBuf iterator
232+
pub struct RingBufIterator<'self, T> {
233+
priv lo: uint,
234+
priv index: uint,
235+
priv rindex: uint,
236+
priv elts: &'self [Option<T>],
237+
}
222238

223-
#[inline]
224-
fn size_hint(&self) -> (uint, Option<uint>) {
225-
let len = self.rindex - self.index;
226-
(len, Some(len))
227-
}
239+
impl<'self, T> Iterator<&'self T> for RingBufIterator<'self, T> {
240+
#[inline]
241+
fn next(&mut self) -> Option<&'self T> {
242+
if self.index == self.rindex {
243+
return None;
228244
}
245+
let raw_index = raw_index(self.lo, self.elts.len(), self.index);
246+
self.index += 1;
247+
Some(self.elts[raw_index].get_ref())
229248
}
230-
}
231249

232-
macro_rules! iterator_rev {
233-
(impl $name:ident -> $elem:ty, $getter:ident) => {
234-
impl<'self, T> DoubleEndedIterator<$elem> for $name<'self, T> {
235-
#[inline]
236-
fn next_back(&mut self) -> Option<$elem> {
237-
if self.index == self.rindex {
238-
return None;
239-
}
240-
self.rindex -= 1;
241-
let raw_index = raw_index(self.lo, self.elts.len(), self.rindex);
242-
Some(self.elts[raw_index] . $getter ())
243-
}
244-
}
250+
#[inline]
251+
fn size_hint(&self) -> (uint, Option<uint>) {
252+
let len = self.rindex - self.index;
253+
(len, Some(len))
245254
}
246255
}
247256

248-
249-
/// RingBuf iterator
250-
pub struct RingBufIterator<'self, T> {
251-
priv lo: uint,
252-
priv index: uint,
253-
priv rindex: uint,
254-
priv elts: &'self [Option<T>],
257+
impl<'self, T> DoubleEndedIterator<&'self T> for RingBufIterator<'self, T> {
258+
#[inline]
259+
fn next_back(&mut self) -> Option<&'self T> {
260+
if self.index == self.rindex {
261+
return None;
262+
}
263+
self.rindex -= 1;
264+
let raw_index = raw_index(self.lo, self.elts.len(), self.rindex);
265+
Some(self.elts[raw_index].get_ref())
266+
}
255267
}
256-
iterator!{impl RingBufIterator -> &'self T, get_ref}
257-
iterator_rev!{impl RingBufIterator -> &'self T, get_ref}
258268

259269
impl<'self, T> ExactSize<&'self T> for RingBufIterator<'self, T> {}
260270

@@ -275,13 +285,49 @@ impl<'self, T> RandomAccessIterator<&'self T> for RingBufIterator<'self, T> {
275285

276286
/// RingBuf mutable iterator
277287
pub struct RingBufMutIterator<'self, T> {
278-
priv lo: uint,
279-
priv index: uint,
280-
priv rindex: uint,
281-
priv elts: &'self mut [Option<T>],
288+
priv remaining1: &'self mut [Option<T>],
289+
priv remaining2: &'self mut [Option<T>],
290+
priv nelts: uint,
291+
}
292+
293+
impl<'self, T> Iterator<&'self mut T> for RingBufMutIterator<'self, T> {
294+
#[inline]
295+
fn next(&mut self) -> Option<&'self mut T> {
296+
if self.nelts == 0 {
297+
return None;
298+
}
299+
let r = if self.remaining1.len() > 0 {
300+
&mut self.remaining1
301+
} else {
302+
assert!(self.remaining2.len() > 0);
303+
&mut self.remaining2
304+
};
305+
self.nelts -= 1;
306+
Some(r.mut_shift_ref().get_mut_ref())
307+
}
308+
309+
#[inline]
310+
fn size_hint(&self) -> (uint, Option<uint>) {
311+
(self.nelts, Some(self.nelts))
312+
}
313+
}
314+
315+
impl<'self, T> DoubleEndedIterator<&'self mut T> for RingBufMutIterator<'self, T> {
316+
#[inline]
317+
fn next_back(&mut self) -> Option<&'self mut T> {
318+
if self.nelts == 0 {
319+
return None;
320+
}
321+
let r = if self.remaining2.len() > 0 {
322+
&mut self.remaining2
323+
} else {
324+
assert!(self.remaining1.len() > 0);
325+
&mut self.remaining1
326+
};
327+
self.nelts -= 1;
328+
Some(r.mut_pop_ref().get_mut_ref())
329+
}
282330
}
283-
iterator!{impl RingBufMutIterator -> &'self mut T, get_mut_ref}
284-
iterator_rev!{impl RingBufMutIterator -> &'self mut T, get_mut_ref}
285331

286332
impl<'self, T> ExactSize<&'self mut T> for RingBufMutIterator<'self, T> {}
287333

@@ -667,6 +713,21 @@ mod tests {
667713
assert_eq!(d.rev_iter().collect::<~[&int]>(), ~[&4,&3,&2,&1,&0,&6,&7,&8]);
668714
}
669715

716+
#[test]
717+
fn test_mut_rev_iter_wrap() {
718+
let mut d = RingBuf::with_capacity(3);
719+
assert!(d.mut_rev_iter().next().is_none());
720+
721+
d.push_back(1);
722+
d.push_back(2);
723+
d.push_back(3);
724+
assert_eq!(d.pop_front(), Some(1));
725+
d.push_back(4);
726+
727+
assert_eq!(d.mut_rev_iter().map(|x| *x).collect::<~[int]>(),
728+
~[4, 3, 2]);
729+
}
730+
670731
#[test]
671732
fn test_mut_iter() {
672733
let mut d = RingBuf::new();

0 commit comments

Comments
 (0)