You cannot do this because it would allow you to circumvent runtime checks for uniqueness violations.
RefCell
provides you a way to "defer" mutability exclusiveness checks to runtime, in exchange allowing mutation of the data it holds inside through shared references. This is done using RAII guards: you can obtain a guard object using a shared reference to RefCell
, and then access the data inside RefCell
using this guard object:
&'a RefCell<T> -> Ref<'a, T> (with borrow) or RefMut<'a, T> (with borrow_mut)
&'b Ref<'a, T> -> &'b T
&'b mut RefMut<'a, T> -> &'b mut T
The key point here is that 'b
is different from 'a
, which allows one to obtain &mut T
references without having a &mut
reference to the RefCell
. However, these references will be linked to the guard instead and can't live longer than the guard. This is done intentionally: Ref
and RefMut
destructors toggle various flags inside their RefCell
to force mutability checks and to force borrow()
and borrow_mut()
panic if these checks fail.
The simplest thing you can do is to return a wrapper around Ref
, a reference to which would implement IntoIterator
:
use std::cell::Ref;
struct VecRefWrapper<'a, T: 'a> {
r: Ref<'a, Vec<T>>
}
impl<'a, 'b: 'a, T: 'a> IntoIterator for &'b VecRefWrapper<'a, T> {
type IntoIter = Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Iter<'a, T> {
self.r.iter()
}
}
(try it on playground)
You can't implement IntoIterator
for VecRefWrapper
directly because then the internal Ref
will be consumed by into_iter()
, giving you essentially the same situation you're in now.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…