【问题标题】:Temporary value dropped while borrowed, but I don't want to do a let借来临时价值下降,但我不想让
【发布时间】:2019-12-05 10:55:35
【问题描述】:

我正在做这样的事情:

fn main() {
    //[1, 0, 0, 0, 99]; // return [2, 0, 0, 0, 99]
    //[2, 3, 0, 3, 99]; // return [2,3,0,6,99]
    //[2, 4, 4, 5, 99, 0]; // return [2,4,4,5,99,9801]
    //[1, 1, 1, 4, 99, 5, 6, 0, 99]; // return [30,1,1,4,2,5,6,0,99]

    let map: Vec<(&mut [usize], &[usize])> = vec![(&mut [1, 0, 0, 0, 99], &[2, 0, 0, 0, 99])];

    for (x, y) in map {
        execute_program(x);
        assert_eq!(x, y);
    }
}

pub fn execute_program(vec: &mut [usize]) {
    //do something inside vec
}

Here the playground

问题是我没有在元组的第一个元素上使用 let,我想借用它来执行程序:

error[E0716]: temporary value dropped while borrowed
 --> src/main.rs:2:57
  |
2 |     let map: Vec<(&mut [usize], &[usize])> = vec![(&mut [1, 0, 0, 0, 99], &[2, 0, 0, 0, 99])];
  |                                                         ^^^^^^^^^^^^^^^^                     - temporary value is freed at the end of this statement
  |                                                         |
  |                                                         creates a temporary which is freed while still in use
3 | 
4 |     for (x, y) in map {
  |                   --- borrow later used here
  |
  = note: consider using a `let` binding to create a longer lived value

但我所做的正是重构,因为我不想为我想测试的每个切片都做一个let

真的需要let 吗?

【问题讨论】:

标签: rust borrowing


【解决方案1】:

嗯,something 必须拥有这些数组中的每一个,因为引用不能拥有这些东西。而且数组的大小不同,所以所有者必须是一个指针。最常见的类数组拥有指针是Vec

let map: Vec<(Vec<usize>, &[usize])> = vec![
    (vec![1, 0, 0, 0, 99], &[2, 0, 0, 0, 99]),
    (vec![2, 3, 0, 3, 99], &[2, 3, 0, 6, 99]),
    (vec![2, 4, 4, 5, 99, 0], &[2, 4, 4, 5, 99, 9801]),
    (vec![1, 1, 1, 4, 99, 5, 6, 0, 99], &[30, 1, 1, 4, 2, 5, 6, 0, 99]),
];

for (mut x, y) in map {
    execute_program(&mut x);
    assert_eq!(x, y);
}

因此,这些数组归 map 所有,并在必要时借用,正如 loganfsmyth 在问题 cmets 中也建议的那样。

您可能会担心进行不必要的分配会降低性能。这是使用单个let的成本;由于数组的大小并不完全相同,因此如果您希望将它们放在堆栈中,则确实没有办法用不同的lets 来声明它们。但是,您可以编写一个删除样板的宏。

等等,为什么它对y有效?

你可能想知道为什么我把x 变成了一个向量,而把y 保持原样。答案是因为y 是共享引用,所以这些数组受制于static promotion,因此&amp;[2, 0, 0, 0, 99] 实际上是&amp;'static [usize; 5] 类型,可以强制转换为&amp;'static [usize]&amp;mut 引用不会触发静态提升,因为在没有某种同步的情况下改变静态值是不安全的。

【讨论】:

    猜你喜欢
    • 2021-03-05
    • 1970-01-01
    • 2023-03-15
    • 1970-01-01
    • 2021-05-05
    • 2022-01-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多