可变借用在循环的前一次迭代中从这里开始

mutable borrow starts here in previous iteration of loop

这里是 Rust 新手,我在 Whosebug 中寻找过类似的案例(而且有很多),但它们的场景都略有不同,我想不出解决这个问题的方法。

我试图遍历一些字符串,将它们传递给一个函数,该函数对它们应用一些操作并最终将结果推送到一个向量中。 (实际情况对于 map 场景来说太复杂了)。

playground

mod lifetime_test {
    fn parse_line<'a>(item: &'a str, target: &'a mut Vec<&'a str>) {
        // ... use item to compute a result
        target.push("result");
    }

    fn parse_file() {
        let mut target: Vec<&str> = Vec::new();
        let source: Vec<&str> = Vec::new();

        // ... fill source with strings from file

        for item in source {
            parse_line(item, &mut target);
        }
    }
}

fn main() {}

以上不编译:mutable borrow starts here in previous iteration of loopparse_line 调用。

我想我明白为什么它抱怨多次可变借用,但我找不到一种方法来传递字符串和向量,并让 parse_line 函数将其结果存储到传递的向量中。

在实际情况下,parse_line 函数很复杂,它可能会或可能不会将值添加到几个向量中,所以我认为制作 parse_line return 多个值会使理解起来更复杂。所以我宁愿传递 vector(2) 并让 parse_line 决定它是否需要添加新值。

变化:

fn parse_line<'a>(item: &'a str, target: &'a mut Vec<&'a str>)

收件人:

fn parse_line<'a>(item: &'a str, target: &mut Vec<&'a str>)

仅仅因为您有一个在某个生命周期内通用的函数 'a 并不意味着该函数使用的每个引用实际上都必须具有 'a 生命周期。 target 的可变借用的生命周期必须短于或等于 'a,但您不希望它相等,因为它会严重限制您的代码(而且完全没有必要),因此,只要您从 target 的可变借用中删除 'a 注释,编译器就会推断出可变借用的适当生命周期,并且代码会编译:

fn parse_line<'a>(item: &'a str, target: &mut Vec<&'a str>) {
    // ... use item to compute a result
    target.push("result");
}

fn parse_file() {
    let mut target: Vec<&str> = Vec::new();
    let source: Vec<&str> = Vec::new();

    // ... fill source with strings from file

    for item in source {
        parse_line(item, &mut target);
    }
}

playground