]> git.proxmox.com Git - rustc.git/blame - src/libcore/ops/drop.rs
New upstream version 1.42.0+dfsg1
[rustc.git] / src / libcore / ops / drop.rs
CommitLineData
3b2f2976 1/// Used to run some code when a value goes out of scope.
041b39d2
XL
2/// This is sometimes called a 'destructor'.
3///
3b2f2976
XL
4/// When a value goes out of scope, it will have its `drop` method called if
5/// its type implements `Drop`. Then, any fields the value contains will also
041b39d2
XL
6/// be dropped recursively.
7///
3b2f2976 8/// Because of this recursive dropping, you do not need to implement this trait
041b39d2
XL
9/// unless your type needs its own destructor logic.
10///
3b2f2976
XL
11/// Refer to [the chapter on `Drop` in *The Rust Programming Language*][book]
12/// for some more elaboration.
13///
0731742a 14/// [book]: ../../book/ch15-03-drop.html
3b2f2976 15///
041b39d2
XL
16/// # Examples
17///
3b2f2976
XL
18/// ## Implementing `Drop`
19///
20/// The `drop` method is called when `_x` goes out of scope, and therefore
21/// `main` prints `Dropping!`.
041b39d2
XL
22///
23/// ```
24/// struct HasDrop;
25///
26/// impl Drop for HasDrop {
27/// fn drop(&mut self) {
28/// println!("Dropping!");
29/// }
30/// }
31///
32/// fn main() {
33/// let _x = HasDrop;
34/// }
35/// ```
36///
3b2f2976
XL
37/// ## Dropping is done recursively
38///
39/// When `outer` goes out of scope, the `drop` method will be called first for
40/// `Outer`, then for `Inner`. Therefore, `main` prints `Dropping Outer!` and
41/// then `Dropping Inner!`.
041b39d2
XL
42///
43/// ```
44/// struct Inner;
45/// struct Outer(Inner);
46///
47/// impl Drop for Inner {
48/// fn drop(&mut self) {
49/// println!("Dropping Inner!");
50/// }
51/// }
52///
53/// impl Drop for Outer {
54/// fn drop(&mut self) {
55/// println!("Dropping Outer!");
56/// }
57/// }
58///
59/// fn main() {
60/// let _x = Outer(Inner);
61/// }
62/// ```
63///
3b2f2976
XL
64/// ## Variables are dropped in reverse order of declaration
65///
66/// `_first` is declared first and `_second` is declared second, so `main` will
67/// print `Declared second!` and then `Declared first!`.
041b39d2
XL
68///
69/// ```
70/// struct PrintOnDrop(&'static str);
71///
3b2f2976
XL
72/// impl Drop for PrintOnDrop {
73/// fn drop(&mut self) {
74/// println!("{}", self.0);
75/// }
76/// }
77///
041b39d2
XL
78/// fn main() {
79/// let _first = PrintOnDrop("Declared first!");
80/// let _second = PrintOnDrop("Declared second!");
81/// }
82/// ```
83#[lang = "drop"]
84#[stable(feature = "rust1", since = "1.0.0")]
85pub trait Drop {
3b2f2976
XL
86 /// Executes the destructor for this type.
87 ///
0531ce1d 88 /// This method is called implicitly when the value goes out of scope,
3b2f2976
XL
89 /// and cannot be called explicitly (this is compiler error [E0040]).
90 /// However, the [`std::mem::drop`] function in the prelude can be
91 /// used to call the argument's `Drop` implementation.
041b39d2
XL
92 ///
93 /// When this method has been called, `self` has not yet been deallocated.
3b2f2976
XL
94 /// That only happens after the method is over.
95 /// If this wasn't the case, `self` would be a dangling reference.
041b39d2 96 ///
3b2f2976 97 /// # Panics
041b39d2 98 ///
3b2f2976
XL
99 /// Given that a [`panic!`] will call `drop` as it unwinds, any [`panic!`]
100 /// in a `drop` implementation will likely abort.
041b39d2 101 ///
dfeec247
XL
102 /// Note that even if this panics, the value is considered to be dropped;
103 /// you must not cause `drop` to be called again. This is normally automatically
104 /// handled by the compiler, but when using unsafe code, can sometimes occur
105 /// unintentionally, particularly when using [`std::ptr::drop_in_place`].
106 ///
041b39d2 107 /// [E0040]: ../../error-index.html#E0040
3b2f2976 108 /// [`panic!`]: ../macro.panic.html
041b39d2 109 /// [`std::mem::drop`]: ../../std/mem/fn.drop.html
dfeec247 110 /// [`std::ptr::drop_in_place`]: ../../std/ptr/fn.drop_in_place.html
041b39d2
XL
111 #[stable(feature = "rust1", since = "1.0.0")]
112 fn drop(&mut self);
113}