静态引用结构

时间:2019-12-16 16:53:21

标签: rust reference static borrow-checker

为什么这两个相似的代码块的行为不同?

struct SomeData {
    id: u32,
}

struct ComplexFoo {
    some_data: SomeData,
}

static mut SELECTED_STRATEGY: &ComplexFoo = &ComplexFoo {
    some_data: SomeData { id: 1 },
};

案例A(编译)

pub fn main() {
    unsafe {
        SELECTED_STRATEGY = &ComplexFoo {
            some_data: SomeData { id: 2 },
        };
    }
}

案例B

pub fn run() {
    unsafe {
        let some_data = SomeData { id: 2 };
        SELECTED_STRATEGY = &ComplexFoo { some_data };
    }
}

不编译:

error[E0716]: temporary value dropped while borrowed
  --> src/lib.rs:16:30
   |
16 |         SELECTED_STRATEGY = &ComplexFoo { some_data };
   |         ---------------------^^^^^^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement
   |         |                    |
   |         |                    creates a temporary which is freed while still in use
   |         assignment requires that borrow lasts for `'static`

my previous question,我想我知道发生了什么事,但是我想证实我的理解。这个解释正确吗?

SELECTED_STRATEGY在声明时初始化,由于它是静态的,因此&ComplexFoo { some_data: SomeData { id: 1 } }的实例在编译时发生。

然后在情况A 中,即使分配在运行时发生,由于静态提升,ComplexFoo { some_data: SomeData { id: 2 } }的实例也是在编译时创建的。在运行时不会发生实际分配,并且在作用域末尾不会删除任何数据。发生的一切只是一个指针开关。

将其与情况B (在编译时无法创建&ComplexFoo { some_data }的地方进行对比,因为some_data是在堆栈上创建的。为什么也不能静态提升SomeData { id: 2 }?因为它具有要删除的实际所有者some_data,但是在这种情况下,它将尝试将其移至ComplexFoo结构中。我想现在SELECTED_STRATEGY只能被分配具有'static生命周期的值,但是&ComplexFoo { some_data }会创建一个没有静态生命周期的临时值,并且会在本地作用域的末尾丢弃。 / p>

0 个答案:

没有答案