Cast要求变量被借用为'static。

3
pub struct IterOverVecVec<'a> {
    m: &'a dyn IterTrait,
}

impl<'a> Iterator for IterOverVecVec<'a> {
    type Item = u16;
    fn next(&mut self) -> Option<Self::Item> {
        Some(1)
    }
}

impl<'a> IterOverVecVec<'a> {
    fn new(m: &'a dyn IterTrait) -> Self {
        Self { m }
    }
}

pub trait IterTrait {}

impl<'b> dyn IterTrait {
    pub fn get_iter<'a>(&'a self) -> IterOverVecVec<'a> {
        IterOverVecVec::new(self)
    }
}

pub struct HasAVec<'a> {
    m: &'a Vec<Vec<u16>>,
}

impl<'a> IterTrait for HasAVec<'a> {}

impl<'a> HasAVec<'a> {
    pub fn new(m: &'a Vec<Vec<u16>>) -> Self {
        Self { m }
    }
}

#[test]
fn fails() {
    let vecvec: Vec<Vec<u16>> = vec![vec![1, 2, 3], vec![4, 5, 6]];
    let struct_with_vecs = HasAVec::new(&vecvec);
    let ni = <dyn IterTrait>::get_iter(&struct_with_vecs);
}

error[E0597]: `vecvec` does not live long enough
  --> src/lib.rs:41:41
   |
41 |     let struct_with_vecs = HasAVec::new(&vecvec);
   |                                         ^^^^^^^ borrowed value does not live long enough
42 |     let ni = <dyn IterTrait>::get_iter(&struct_with_vecs);
   |                                        ----------------- cast requires that `vecvec` is borrowed for `'static`
43 | }
   | - `vecvec` dropped here while still borrowed

游乐场链接: https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=5d7b88a4a261821fabfd0228e8ef8b2c

我对根本原因的理解是:在第33行将struct_with_vecs转换为特征类型之后,编译器会尝试推断它的(新?)生命周期,并以某种方式得出'static,由于我没有正确的生命周期注释,它就报错了。

我找到的问题最相近的是一个 Rust 论坛线程 (https://users.rust-lang.org/t/argument-requires-that-is-borrowed-for-static/66503/2),如果我理解正确,它说在这种情况下,Rust 会尝试应用最长可能的生命周期。然而,我无法将那个问题中的解决方案应用到我的问题上,因为似乎是由我没有使用的闭包引起的。

所以我的问题是,我该如何使用IterTrait::get_iter()而不让vecvec被借用到'static?

1个回答

1

rustc到达'static的原因是因为dyn Traitdyn Trait + 'static。如果要允许其他生命周期,您应该使用dyn Trait + 'lifetime或带有省略生命周期的dyn Trait + '_

如果您替换

impl dyn IterTrait {

使用

impl dyn IterTrait + '_ {

然后它就可以工作了(游乐场)。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接