指向 Result<Vec<f64> 中向量的第一个元素的指针,_> 已损坏
Pointer to first element of vector in Result<Vec<f64>, _> is corrupted
我有一个Result<Vec<f64>, _>
。当我尝试提取指向实际 f64
数组的指针时,我观察到 dptr
指向的数组是预期数组的损坏版本(前 10 个字节已更改)。
为什么会发生这种情况,我该如何避免?
use std::error::Error;
fn main() {
let res: Result<Vec<f64>, Box<dyn Error>> = Ok(vec![1., 2., 3., 4.]);
let dptr: *const f64 = match res {
Ok(v) => &v[0],
Err(_) => std::ptr::null(),
};
assert_eq!(unsafe { *dptr }, 1.0);
}
结果:
thread 'main' panicked at 'assertion failed: `(left == right)`
left: `0.0`,
right: `1.0`', src/main.rs:9:5
该程序的行为是未定义的,可以在 Miri 下 运行 看到它,Miri 是一个 Rust 解释器,有时可以检测到未定义的行为。 (您可以在 playground 中点击“工具”(右上角)->“Miri”):
error: Undefined Behavior: pointer to alloc1039 was dereferenced after this allocation got freed
--> src/main.rs:9:25
|
9 | assert_eq!(unsafe { *dptr }, 1.0);
| ^^^^^ pointer to alloc1039 was dereferenced after this allocation got freed
|
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
这里发生的是释放后使用:Ok(v) => &v[0],
行从 v
(因此 res
)移动数据,导致它被释放。后来,用于其他变量的数据覆盖了现有数据(因为在它指向的内存被释放后使用指针是未定义的行为)。
如果您尝试在没有 unsafe
的情况下以正常方式从 res
中读取数据,您将在这个问题上遇到编译时错误:
error[E0382]: use of partially moved value: `res`
--> src/main.rs:9:10
|
6 | Ok(v) => &v[0],
| - value partially moved here
...
9 | dbg!(res.unwrap()[0]);
| ^^^ value used here after partial move
|
= note: partial move occurs because value has type `Vec<f64>`, which does not implement the `Copy` trait
help: borrow this field in the pattern to avoid moving `res.0`
|
6 | Ok(ref v) => &v[0],
| +++
我有一个Result<Vec<f64>, _>
。当我尝试提取指向实际 f64
数组的指针时,我观察到 dptr
指向的数组是预期数组的损坏版本(前 10 个字节已更改)。
为什么会发生这种情况,我该如何避免?
use std::error::Error;
fn main() {
let res: Result<Vec<f64>, Box<dyn Error>> = Ok(vec![1., 2., 3., 4.]);
let dptr: *const f64 = match res {
Ok(v) => &v[0],
Err(_) => std::ptr::null(),
};
assert_eq!(unsafe { *dptr }, 1.0);
}
结果:
thread 'main' panicked at 'assertion failed: `(left == right)`
left: `0.0`,
right: `1.0`', src/main.rs:9:5
该程序的行为是未定义的,可以在 Miri 下 运行 看到它,Miri 是一个 Rust 解释器,有时可以检测到未定义的行为。 (您可以在 playground 中点击“工具”(右上角)->“Miri”):
error: Undefined Behavior: pointer to alloc1039 was dereferenced after this allocation got freed
--> src/main.rs:9:25
|
9 | assert_eq!(unsafe { *dptr }, 1.0);
| ^^^^^ pointer to alloc1039 was dereferenced after this allocation got freed
|
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
这里发生的是释放后使用:Ok(v) => &v[0],
行从 v
(因此 res
)移动数据,导致它被释放。后来,用于其他变量的数据覆盖了现有数据(因为在它指向的内存被释放后使用指针是未定义的行为)。
如果您尝试在没有 unsafe
的情况下以正常方式从 res
中读取数据,您将在这个问题上遇到编译时错误:
error[E0382]: use of partially moved value: `res`
--> src/main.rs:9:10
|
6 | Ok(v) => &v[0],
| - value partially moved here
...
9 | dbg!(res.unwrap()[0]);
| ^^^ value used here after partial move
|
= note: partial move occurs because value has type `Vec<f64>`, which does not implement the `Copy` trait
help: borrow this field in the pattern to avoid moving `res.0`
|
6 | Ok(ref v) => &v[0],
| +++