我想知道有没有一种方法可以确定一个变量是在堆栈上还是在堆上分配的。
考虑以下代码:
struct SomeStruct;
fn main() {
let some_thing = Box::new(SomeStruct);
println!("{:p}", some_thing);
foo(&*some_thing);
}
fn foo (bar: &SomeStruct) {
println!("{:p}", bar);
}
打印
0x1
0x1
然后
struct SomeStruct;
fn main() {
let some_thing = &SomeStruct;
println!("{:p}", some_thing);
foo(some_thing);
}
fn foo (bar: &SomeStruct) {
println!("{:p}", bar);
}
打印
0x10694dcc0
0x10694dcc0
我能看到堆分配版本的内存地址要短得多,但我不知道这是否是一种可靠的区分方法。我想知道是否有类似 std::foo::is_heap_allocated()
的东西。
0x1
是Rust分配器为零大小对象返回的虚拟地址,不在堆上。详见[heap.rs#L90](https://github.com/rust-lang/rust/blob/9ecc9896dedb426e3f4eb3d23dfc60192fe5275f/src/liballoc/heap.rs#L90)。 - Denilson Amorimnum
和dog
在堆栈上,zoo
是一个数组,所以它也在堆栈上,而Vec
的“存储缓冲区”虽然是在堆上分配的,但你只打印了 Vec 结构本身的地址(一个指针、一个长度和一个容量的三元组),而这个结构体本身是在堆栈上的。 - MasklinnVec
类型有点像指针,但它并没有实现Pointer
接口。但是,切片类型实现了该接口,因此如果你打印&*mutant_zoo
(或者mutant_zoo.as_slice()
),你将得到 vec 堆缓冲区的地址。mutant_zoo.as_ptr()
也可以工作,因为它返回 vec 缓冲区的原始指针。 - Masklinn