tezvyn:

Rust's `Drop` Trait: Automatic Resource Cleanup

AI-drafted, machine-checkedSource: doc.rust-lang.orgintermediate

Rust's `Drop` trait provides automatic, deterministic cleanup, like a destructor. It's used to release external resources like file handles or network sockets when a value goes out of scope. The key footgun: you cannot implement `Drop` on a `Copy` type.

WHY IT EXISTS Languages need a way to manage resources like memory, file handles, or network connections. Instead of relying on a garbage collector or manual cleanup calls, Rust uses the ownership system combined with the Drop trait. This enables a pattern called RAII (Resource Acquisition Is Initialization), where resource cleanup is tied to an object's lifetime, making leaks much harder.

THE MENTAL MODEL Think of a type with a Drop implementation as a self-cleaning tool. When you're finished using it and it goes out of scope, it automatically cleans itself up and returns its resources. You don't have to remember to call file.close() because the File type's Drop implementation handles it for you the moment the variable is no longer needed.

HOW IT WORKS To define custom cleanup logic, you implement the drop(&mut self) method for your type. When a value of that type goes out of scope, Rust automatically calls your drop method. Afterwards, it recursively drops each of the struct's fields. The drop order is guaranteed: for local variables, it's Last-In, First-Out (reverse order of declaration). For struct fields, it's the same order they are declared in the struct definition.

WHEN TO USE IT Implement Drop when your type directly manages a resource that Rust doesn't know how to clean up on its own. This is common for types that wrap raw pointers from a C library, or manage low-level OS resources like file descriptors or sockets. Most of the time, you don't need it, as composing standard library types like Vec or Box is enough; the compiler will generate the necessary drop logic for you.

WHEN NOT TO USE IT You cannot implement Drop on a type that also implements Copy. The two are mutually exclusive because if a type can be trivially bit-copied, it becomes ambiguous which copy is responsible for cleaning up the resource. You also cannot call the drop method directly for safety reasons; if you need to force a value to be dropped early, use the global function std::mem::drop().

ONE CANONICAL EXAMPLE The standard library's std::fs::File is the classic example. When you open a file, a File struct is returned which holds onto the operating system's file handle. The File struct implements Drop, and its drop method ensures the underlying file is closed. This happens automatically when the File variable goes out of scope, preventing resource leaks even in the case of panics.

Read the original → doc.rust-lang.org

Get five bites like this every day.

Tezvyn delivers a daily feed of 60-second tech bites with quizzes to lock in what you learn.