直接回答:Drop::drop 在值离开作用域时由编译器自动调用,是 RAII 的落点:文件、锁、堆内存通过所有权与作用域绑定,析构即释放。析构顺序有明确规定:局部变量按声明的逆序 drop;结构体字段按声明顺序 drop;嵌套结构先内层后外层。这个顺序可以依赖——守卫必须晚于它所保护的数据析构。
展开解析:不能手动调 x.drop()(编译器保留方法,直接调报 E0040),要提前析构用 std::mem::drop(x) 取走所有权,常用于尽早释放锁。ManuallyDrop<T> 阻止自动析构,用于 union、FFI 场景。实现了 Drop 的类型不能再把字段 move 出去(部分移动受限),因为析构时还需要完整对象。panic 展开时局部变量同样按序 drop,所以 RAII 守卫在错误路径下也能正确清理。Rc 循环引用永远不会触发 Drop,那是内存泄漏而非未定义行为。
struct Guard(&'static str);
impl Drop for Guard {
fn drop(&mut self) { println!("drop {}", self.0); }
}
let _a = Guard("a");
let _b = Guard("b"); // 作用域结束输出:drop b → drop a(逆序)
追问方向:Drop 与 panic 栈展开如何交互?为什么锁守卫的释放顺序重要?mem::forget 的用途与风险?
(约 530 字)