]> git.proxmox.com Git - rustc.git/blame - src/libcore/ops/deref.rs
New upstream version 1.31.0~beta.4+dfsg1
[rustc.git] / src / libcore / ops / deref.rs
CommitLineData
041b39d2
XL
1// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
2// file at the top-level directory of this distribution and at
3// http://rust-lang.org/COPYRIGHT.
4//
5// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8// option. This file may not be copied, modified, or distributed
9// except according to those terms.
10
3b2f2976 11/// Used for immutable dereferencing operations, like `*v`.
041b39d2 12///
3b2f2976
XL
13/// In addition to being used for explicit dereferencing operations with the
14/// (unary) `*` operator in immutable contexts, `Deref` is also used implicitly
15/// by the compiler in many circumstances. This mechanism is called
16/// ['`Deref` coercion'][more]. In mutable contexts, [`DerefMut`] is used.
041b39d2 17///
3b2f2976
XL
18/// Implementing `Deref` for smart pointers makes accessing the data behind them
19/// convenient, which is why they implement `Deref`. On the other hand, the
20/// rules regarding `Deref` and [`DerefMut`] were designed specifically to
abe05a73 21/// accommodate smart pointers. Because of this, **`Deref` should only be
3b2f2976
XL
22/// implemented for smart pointers** to avoid confusion.
23///
24/// For similar reasons, **this trait should never fail**. Failure during
25/// dereferencing can be extremely confusing when `Deref` is invoked implicitly.
26///
27/// # More on `Deref` coercion
28///
29/// If `T` implements `Deref<Target = U>`, and `x` is a value of type `T`, then:
30///
31/// * In immutable contexts, `*x` on non-pointer types is equivalent to
32/// `*Deref::deref(&x)`.
33/// * Values of type `&T` are coerced to values of type `&U`
34/// * `T` implicitly implements all the (immutable) methods of the type `U`.
35///
36/// For more details, visit [the chapter in *The Rust Programming Language*]
37/// [book] as well as the reference sections on [the dereference operator]
ff7c6d11 38/// [ref-deref-op], [method resolution] and [type coercions].
3b2f2976
XL
39///
40/// [book]: ../../book/second-edition/ch15-02-deref.html
41/// [`DerefMut`]: trait.DerefMut.html
42/// [more]: #more-on-deref-coercion
ea8adc8c 43/// [ref-deref-op]: ../../reference/expressions/operator-expr.html#the-dereference-operator
ff7c6d11 44/// [method resolution]: ../../reference/expressions/method-call-expr.html
3b2f2976 45/// [type coercions]: ../../reference/type-coercions.html
041b39d2
XL
46///
47/// # Examples
48///
3b2f2976 49/// A struct with a single field which is accessible by dereferencing the
041b39d2
XL
50/// struct.
51///
52/// ```
53/// use std::ops::Deref;
54///
55/// struct DerefExample<T> {
56/// value: T
57/// }
58///
59/// impl<T> Deref for DerefExample<T> {
60/// type Target = T;
61///
62/// fn deref(&self) -> &T {
63/// &self.value
64/// }
65/// }
66///
3b2f2976
XL
67/// let x = DerefExample { value: 'a' };
68/// assert_eq!('a', *x);
041b39d2
XL
69/// ```
70#[lang = "deref"]
83c7162d
XL
71#[doc(alias = "*")]
72#[doc(alias = "&*")]
041b39d2
XL
73#[stable(feature = "rust1", since = "1.0.0")]
74pub trait Deref {
3b2f2976 75 /// The resulting type after dereferencing.
041b39d2
XL
76 #[stable(feature = "rust1", since = "1.0.0")]
77 type Target: ?Sized;
78
3b2f2976 79 /// Dereferences the value.
83c7162d 80 #[must_use]
041b39d2
XL
81 #[stable(feature = "rust1", since = "1.0.0")]
82 fn deref(&self) -> &Self::Target;
83}
84
85#[stable(feature = "rust1", since = "1.0.0")]
0bf4aa26 86impl<T: ?Sized> Deref for &T {
041b39d2
XL
87 type Target = T;
88
89 fn deref(&self) -> &T { *self }
90}
91
92#[stable(feature = "rust1", since = "1.0.0")]
0bf4aa26 93impl<T: ?Sized> Deref for &mut T {
041b39d2
XL
94 type Target = T;
95
96 fn deref(&self) -> &T { *self }
97}
98
3b2f2976 99/// Used for mutable dereferencing operations, like in `*v = 1;`.
041b39d2 100///
3b2f2976
XL
101/// In addition to being used for explicit dereferencing operations with the
102/// (unary) `*` operator in mutable contexts, `DerefMut` is also used implicitly
103/// by the compiler in many circumstances. This mechanism is called
104/// ['`Deref` coercion'][more]. In immutable contexts, [`Deref`] is used.
041b39d2 105///
3b2f2976
XL
106/// Implementing `DerefMut` for smart pointers makes mutating the data behind
107/// them convenient, which is why they implement `DerefMut`. On the other hand,
108/// the rules regarding [`Deref`] and `DerefMut` were designed specifically to
abe05a73 109/// accommodate smart pointers. Because of this, **`DerefMut` should only be
3b2f2976
XL
110/// implemented for smart pointers** to avoid confusion.
111///
112/// For similar reasons, **this trait should never fail**. Failure during
113/// dereferencing can be extremely confusing when `DerefMut` is invoked
114/// implicitly.
115///
116/// # More on `Deref` coercion
117///
118/// If `T` implements `DerefMut<Target = U>`, and `x` is a value of type `T`,
119/// then:
120///
121/// * In mutable contexts, `*x` on non-pointer types is equivalent to
122/// `*Deref::deref(&x)`.
123/// * Values of type `&mut T` are coerced to values of type `&mut U`
124/// * `T` implicitly implements all the (mutable) methods of the type `U`.
125///
126/// For more details, visit [the chapter in *The Rust Programming Language*]
127/// [book] as well as the reference sections on [the dereference operator]
ff7c6d11 128/// [ref-deref-op], [method resolution] and [type coercions].
3b2f2976
XL
129///
130/// [book]: ../../book/second-edition/ch15-02-deref.html
131/// [`Deref`]: trait.Deref.html
132/// [more]: #more-on-deref-coercion
ea8adc8c 133/// [ref-deref-op]: ../../reference/expressions/operator-expr.html#the-dereference-operator
ff7c6d11 134/// [method resolution]: ../../reference/expressions/method-call-expr.html
3b2f2976 135/// [type coercions]: ../../reference/type-coercions.html
041b39d2
XL
136///
137/// # Examples
138///
3b2f2976 139/// A struct with a single field which is modifiable by dereferencing the
041b39d2
XL
140/// struct.
141///
142/// ```
143/// use std::ops::{Deref, DerefMut};
144///
145/// struct DerefMutExample<T> {
146/// value: T
147/// }
148///
149/// impl<T> Deref for DerefMutExample<T> {
150/// type Target = T;
151///
152/// fn deref(&self) -> &T {
153/// &self.value
154/// }
155/// }
156///
157/// impl<T> DerefMut for DerefMutExample<T> {
158/// fn deref_mut(&mut self) -> &mut T {
159/// &mut self.value
160/// }
161/// }
162///
3b2f2976
XL
163/// let mut x = DerefMutExample { value: 'a' };
164/// *x = 'b';
165/// assert_eq!('b', *x);
041b39d2
XL
166/// ```
167#[lang = "deref_mut"]
83c7162d 168#[doc(alias = "*")]
041b39d2
XL
169#[stable(feature = "rust1", since = "1.0.0")]
170pub trait DerefMut: Deref {
3b2f2976 171 /// Mutably dereferences the value.
041b39d2
XL
172 #[stable(feature = "rust1", since = "1.0.0")]
173 fn deref_mut(&mut self) -> &mut Self::Target;
174}
175
176#[stable(feature = "rust1", since = "1.0.0")]
0bf4aa26 177impl<T: ?Sized> DerefMut for &mut T {
041b39d2
XL
178 fn deref_mut(&mut self) -> &mut T { *self }
179}