]> git.lizzy.rs Git - rust.git/blob - src/libcore/ops.rs
replace `Neg` example with something more evocative of negation
[rust.git] / src / libcore / ops.rs
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
11 //! Overloadable operators.
12 //!
13 //! Implementing these traits allows you to get an effect similar to
14 //! overloading operators.
15 //!
16 //! Some of these traits are imported by the prelude, so they are available in
17 //! every Rust program.
18 //!
19 //! Many of the operators take their operands by value. In non-generic
20 //! contexts involving built-in types, this is usually not a problem.
21 //! However, using these operators in generic code, requires some
22 //! attention if values have to be reused as opposed to letting the operators
23 //! consume them. One option is to occasionally use `clone()`.
24 //! Another option is to rely on the types involved providing additional
25 //! operator implementations for references. For example, for a user-defined
26 //! type `T` which is supposed to support addition, it is probably a good
27 //! idea to have both `T` and `&T` implement the traits `Add<T>` and `Add<&T>`
28 //! so that generic code can be written without unnecessary cloning.
29 //!
30 //! # Examples
31 //!
32 //! This example creates a `Point` struct that implements `Add` and `Sub`, and
33 //! then demonstrates adding and subtracting two `Point`s.
34 //!
35 //! ```rust
36 //! use std::ops::{Add, Sub};
37 //!
38 //! #[derive(Debug)]
39 //! struct Point {
40 //!     x: i32,
41 //!     y: i32,
42 //! }
43 //!
44 //! impl Add for Point {
45 //!     type Output = Point;
46 //!
47 //!     fn add(self, other: Point) -> Point {
48 //!         Point {x: self.x + other.x, y: self.y + other.y}
49 //!     }
50 //! }
51 //!
52 //! impl Sub for Point {
53 //!     type Output = Point;
54 //!
55 //!     fn sub(self, other: Point) -> Point {
56 //!         Point {x: self.x - other.x, y: self.y - other.y}
57 //!     }
58 //! }
59 //! fn main() {
60 //!     println!("{:?}", Point {x: 1, y: 0} + Point {x: 2, y: 3});
61 //!     println!("{:?}", Point {x: 1, y: 0} - Point {x: 2, y: 3});
62 //! }
63 //! ```
64 //!
65 //! See the documentation for each trait for a minimum implementation that
66 //! prints something to the screen.
67
68 #![stable(feature = "rust1", since = "1.0.0")]
69
70 use cmp::PartialOrd;
71 use fmt;
72 use marker::{Sized, Unsize};
73
74 /// The `Drop` trait is used to run some code when a value goes out of scope.
75 /// This is sometimes called a 'destructor'.
76 ///
77 /// # Examples
78 ///
79 /// A trivial implementation of `Drop`. The `drop` method is called when `_x`
80 /// goes out of scope, and therefore `main` prints `Dropping!`.
81 ///
82 /// ```
83 /// struct HasDrop;
84 ///
85 /// impl Drop for HasDrop {
86 ///     fn drop(&mut self) {
87 ///         println!("Dropping!");
88 ///     }
89 /// }
90 ///
91 /// fn main() {
92 ///     let _x = HasDrop;
93 /// }
94 /// ```
95 #[lang = "drop"]
96 #[stable(feature = "rust1", since = "1.0.0")]
97 pub trait Drop {
98     /// A method called when the value goes out of scope.
99     ///
100     /// When this method has been called, `self` has not yet been deallocated.
101     /// If it were, `self` would be a dangling reference.
102     ///
103     /// After this function is over, the memory of `self` will be deallocated.
104     ///
105     /// # Panics
106     ///
107     /// Given that a `panic!` will call `drop()` as it unwinds, any `panic!` in
108     /// a `drop()` implementation will likely abort.
109     #[stable(feature = "rust1", since = "1.0.0")]
110     fn drop(&mut self);
111 }
112
113 // implements the unary operator "op &T"
114 // based on "op T" where T is expected to be `Copy`able
115 macro_rules! forward_ref_unop {
116     (impl $imp:ident, $method:ident for $t:ty) => {
117         #[stable(feature = "rust1", since = "1.0.0")]
118         impl<'a> $imp for &'a $t {
119             type Output = <$t as $imp>::Output;
120
121             #[inline]
122             fn $method(self) -> <$t as $imp>::Output {
123                 $imp::$method(*self)
124             }
125         }
126     }
127 }
128
129 // implements binary operators "&T op U", "T op &U", "&T op &U"
130 // based on "T op U" where T and U are expected to be `Copy`able
131 macro_rules! forward_ref_binop {
132     (impl $imp:ident, $method:ident for $t:ty, $u:ty) => {
133         #[stable(feature = "rust1", since = "1.0.0")]
134         impl<'a> $imp<$u> for &'a $t {
135             type Output = <$t as $imp<$u>>::Output;
136
137             #[inline]
138             fn $method(self, other: $u) -> <$t as $imp<$u>>::Output {
139                 $imp::$method(*self, other)
140             }
141         }
142
143         #[stable(feature = "rust1", since = "1.0.0")]
144         impl<'a> $imp<&'a $u> for $t {
145             type Output = <$t as $imp<$u>>::Output;
146
147             #[inline]
148             fn $method(self, other: &'a $u) -> <$t as $imp<$u>>::Output {
149                 $imp::$method(self, *other)
150             }
151         }
152
153         #[stable(feature = "rust1", since = "1.0.0")]
154         impl<'a, 'b> $imp<&'a $u> for &'b $t {
155             type Output = <$t as $imp<$u>>::Output;
156
157             #[inline]
158             fn $method(self, other: &'a $u) -> <$t as $imp<$u>>::Output {
159                 $imp::$method(*self, *other)
160             }
161         }
162     }
163 }
164
165 /// The `Add` trait is used to specify the functionality of `+`.
166 ///
167 /// # Examples
168 ///
169 /// A trivial implementation of `Add`. When `Foo + Foo` happens, it ends up
170 /// calling `add`, and therefore, `main` prints `Adding!`.
171 ///
172 /// ```
173 /// use std::ops::Add;
174 ///
175 /// struct Foo;
176 ///
177 /// impl Add for Foo {
178 ///     type Output = Foo;
179 ///
180 ///     fn add(self, _rhs: Foo) -> Foo {
181 ///         println!("Adding!");
182 ///         self
183 ///     }
184 /// }
185 ///
186 /// fn main() {
187 ///     Foo + Foo;
188 /// }
189 /// ```
190 #[lang = "add"]
191 #[stable(feature = "rust1", since = "1.0.0")]
192 pub trait Add<RHS=Self> {
193     /// The resulting type after applying the `+` operator
194     #[stable(feature = "rust1", since = "1.0.0")]
195     type Output;
196
197     /// The method for the `+` operator
198     #[stable(feature = "rust1", since = "1.0.0")]
199     fn add(self, rhs: RHS) -> Self::Output;
200 }
201
202 macro_rules! add_impl {
203     ($($t:ty)*) => ($(
204         #[stable(feature = "rust1", since = "1.0.0")]
205         impl Add for $t {
206             type Output = $t;
207
208             #[inline]
209             #[rustc_inherit_overflow_checks]
210             fn add(self, other: $t) -> $t { self + other }
211         }
212
213         forward_ref_binop! { impl Add, add for $t, $t }
214     )*)
215 }
216
217 add_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
218
219 /// The `Sub` trait is used to specify the functionality of `-`.
220 ///
221 /// # Examples
222 ///
223 /// A trivial implementation of `Sub`. When `Foo - Foo` happens, it ends up
224 /// calling `sub`, and therefore, `main` prints `Subtracting!`.
225 ///
226 /// ```
227 /// use std::ops::Sub;
228 ///
229 /// struct Foo;
230 ///
231 /// impl Sub for Foo {
232 ///     type Output = Foo;
233 ///
234 ///     fn sub(self, _rhs: Foo) -> Foo {
235 ///         println!("Subtracting!");
236 ///         self
237 ///     }
238 /// }
239 ///
240 /// fn main() {
241 ///     Foo - Foo;
242 /// }
243 /// ```
244 #[lang = "sub"]
245 #[stable(feature = "rust1", since = "1.0.0")]
246 pub trait Sub<RHS=Self> {
247     /// The resulting type after applying the `-` operator
248     #[stable(feature = "rust1", since = "1.0.0")]
249     type Output;
250
251     /// The method for the `-` operator
252     #[stable(feature = "rust1", since = "1.0.0")]
253     fn sub(self, rhs: RHS) -> Self::Output;
254 }
255
256 macro_rules! sub_impl {
257     ($($t:ty)*) => ($(
258         #[stable(feature = "rust1", since = "1.0.0")]
259         impl Sub for $t {
260             type Output = $t;
261
262             #[inline]
263             #[rustc_inherit_overflow_checks]
264             fn sub(self, other: $t) -> $t { self - other }
265         }
266
267         forward_ref_binop! { impl Sub, sub for $t, $t }
268     )*)
269 }
270
271 sub_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
272
273 /// The `Mul` trait is used to specify the functionality of `*`.
274 ///
275 /// # Examples
276 ///
277 /// A trivial implementation of `Mul`. When `Foo * Foo` happens, it ends up
278 /// calling `mul`, and therefore, `main` prints `Multiplying!`.
279 ///
280 /// ```
281 /// use std::ops::Mul;
282 ///
283 /// struct Foo;
284 ///
285 /// impl Mul for Foo {
286 ///     type Output = Foo;
287 ///
288 ///     fn mul(self, _rhs: Foo) -> Foo {
289 ///         println!("Multiplying!");
290 ///         self
291 ///     }
292 /// }
293 ///
294 /// fn main() {
295 ///     Foo * Foo;
296 /// }
297 /// ```
298 #[lang = "mul"]
299 #[stable(feature = "rust1", since = "1.0.0")]
300 pub trait Mul<RHS=Self> {
301     /// The resulting type after applying the `*` operator
302     #[stable(feature = "rust1", since = "1.0.0")]
303     type Output;
304
305     /// The method for the `*` operator
306     #[stable(feature = "rust1", since = "1.0.0")]
307     fn mul(self, rhs: RHS) -> Self::Output;
308 }
309
310 macro_rules! mul_impl {
311     ($($t:ty)*) => ($(
312         #[stable(feature = "rust1", since = "1.0.0")]
313         impl Mul for $t {
314             type Output = $t;
315
316             #[inline]
317             #[rustc_inherit_overflow_checks]
318             fn mul(self, other: $t) -> $t { self * other }
319         }
320
321         forward_ref_binop! { impl Mul, mul for $t, $t }
322     )*)
323 }
324
325 mul_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
326
327 /// The `Div` trait is used to specify the functionality of `/`.
328 ///
329 /// # Examples
330 ///
331 /// A trivial implementation of `Div`. When `Foo / Foo` happens, it ends up
332 /// calling `div`, and therefore, `main` prints `Dividing!`.
333 ///
334 /// ```
335 /// use std::ops::Div;
336 ///
337 /// struct Foo;
338 ///
339 /// impl Div for Foo {
340 ///     type Output = Foo;
341 ///
342 ///     fn div(self, _rhs: Foo) -> Foo {
343 ///         println!("Dividing!");
344 ///         self
345 ///     }
346 /// }
347 ///
348 /// fn main() {
349 ///     Foo / Foo;
350 /// }
351 /// ```
352 #[lang = "div"]
353 #[stable(feature = "rust1", since = "1.0.0")]
354 pub trait Div<RHS=Self> {
355     /// The resulting type after applying the `/` operator
356     #[stable(feature = "rust1", since = "1.0.0")]
357     type Output;
358
359     /// The method for the `/` operator
360     #[stable(feature = "rust1", since = "1.0.0")]
361     fn div(self, rhs: RHS) -> Self::Output;
362 }
363
364 macro_rules! div_impl_integer {
365     ($($t:ty)*) => ($(
366         /// This operation rounds towards zero, truncating any
367         /// fractional part of the exact result.
368         #[stable(feature = "rust1", since = "1.0.0")]
369         impl Div for $t {
370             type Output = $t;
371
372             #[inline]
373             fn div(self, other: $t) -> $t { self / other }
374         }
375
376         forward_ref_binop! { impl Div, div for $t, $t }
377     )*)
378 }
379
380 div_impl_integer! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
381
382 macro_rules! div_impl_float {
383     ($($t:ty)*) => ($(
384         #[stable(feature = "rust1", since = "1.0.0")]
385         impl Div for $t {
386             type Output = $t;
387
388             #[inline]
389             fn div(self, other: $t) -> $t { self / other }
390         }
391
392         forward_ref_binop! { impl Div, div for $t, $t }
393     )*)
394 }
395
396 div_impl_float! { f32 f64 }
397
398 /// The `Rem` trait is used to specify the functionality of `%`.
399 ///
400 /// # Examples
401 ///
402 /// A trivial implementation of `Rem`. When `Foo % Foo` happens, it ends up
403 /// calling `rem`, and therefore, `main` prints `Remainder-ing!`.
404 ///
405 /// ```
406 /// use std::ops::Rem;
407 ///
408 /// struct Foo;
409 ///
410 /// impl Rem for Foo {
411 ///     type Output = Foo;
412 ///
413 ///     fn rem(self, _rhs: Foo) -> Foo {
414 ///         println!("Remainder-ing!");
415 ///         self
416 ///     }
417 /// }
418 ///
419 /// fn main() {
420 ///     Foo % Foo;
421 /// }
422 /// ```
423 #[lang = "rem"]
424 #[stable(feature = "rust1", since = "1.0.0")]
425 pub trait Rem<RHS=Self> {
426     /// The resulting type after applying the `%` operator
427     #[stable(feature = "rust1", since = "1.0.0")]
428     type Output = Self;
429
430     /// The method for the `%` operator
431     #[stable(feature = "rust1", since = "1.0.0")]
432     fn rem(self, rhs: RHS) -> Self::Output;
433 }
434
435 macro_rules! rem_impl_integer {
436     ($($t:ty)*) => ($(
437         /// This operation satisfies `n % d == n - (n / d) * d`.  The
438         /// result has the same sign as the left operand.
439         #[stable(feature = "rust1", since = "1.0.0")]
440         impl Rem for $t {
441             type Output = $t;
442
443             #[inline]
444             fn rem(self, other: $t) -> $t { self % other }
445         }
446
447         forward_ref_binop! { impl Rem, rem for $t, $t }
448     )*)
449 }
450
451 rem_impl_integer! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
452
453 macro_rules! rem_impl_float {
454     ($($t:ty)*) => ($(
455         #[stable(feature = "rust1", since = "1.0.0")]
456         impl Rem for $t {
457             type Output = $t;
458
459             #[inline]
460             fn rem(self, other: $t) -> $t { self % other }
461         }
462
463         forward_ref_binop! { impl Rem, rem for $t, $t }
464     )*)
465 }
466
467 rem_impl_float! { f32 f64 }
468
469 /// The `Neg` trait is used to specify the functionality of unary `-`.
470 ///
471 /// # Examples
472 ///
473 /// An implementation of `Neg` for `Sign`, which allows the use of `-` to
474 /// negate its value.
475 ///
476 /// ```
477 /// use std::ops::Neg;
478 ///
479 /// #[derive(Debug, PartialEq)]
480 /// enum Sign {
481 ///     Negative,
482 ///     Zero,
483 ///     Positive,
484 /// }
485 ///
486 /// impl Neg for Sign {
487 ///     type Output = Sign;
488 ///
489 ///     fn neg(self) -> Sign {
490 ///         match self {
491 ///             Sign::Negative => Sign::Positive,
492 ///             Sign::Zero => Sign::Zero,
493 ///             Sign::Positive => Sign::Negative,
494 ///         }
495 ///     }
496 /// }
497 ///
498 /// // a negative positive is a negative
499 /// assert_eq!(-Sign::Positive, Sign::Negative);
500 /// // a double negative is a positive
501 /// assert_eq!(-Sign::Negative, Sign::Positive);
502 /// // zero is its own negation
503 /// assert_eq!(-Sign::Zero, Sign::Zero);
504 /// ```
505 #[lang = "neg"]
506 #[stable(feature = "rust1", since = "1.0.0")]
507 pub trait Neg {
508     /// The resulting type after applying the `-` operator
509     #[stable(feature = "rust1", since = "1.0.0")]
510     type Output;
511
512     /// The method for the unary `-` operator
513     #[stable(feature = "rust1", since = "1.0.0")]
514     fn neg(self) -> Self::Output;
515 }
516
517
518
519 macro_rules! neg_impl_core {
520     ($id:ident => $body:expr, $($t:ty)*) => ($(
521         #[stable(feature = "rust1", since = "1.0.0")]
522         impl Neg for $t {
523             type Output = $t;
524
525             #[inline]
526             #[rustc_inherit_overflow_checks]
527             fn neg(self) -> $t { let $id = self; $body }
528         }
529
530         forward_ref_unop! { impl Neg, neg for $t }
531     )*)
532 }
533
534 macro_rules! neg_impl_numeric {
535     ($($t:ty)*) => { neg_impl_core!{ x => -x, $($t)*} }
536 }
537
538 macro_rules! neg_impl_unsigned {
539     ($($t:ty)*) => {
540         neg_impl_core!{ x => {
541             !x.wrapping_add(1)
542         }, $($t)*} }
543 }
544
545 // neg_impl_unsigned! { usize u8 u16 u32 u64 }
546 neg_impl_numeric! { isize i8 i16 i32 i64 f32 f64 }
547
548 /// The `Not` trait is used to specify the functionality of unary `!`.
549 ///
550 /// # Examples
551 ///
552 /// A trivial implementation of `Not`. When `!Foo` happens, it ends up calling
553 /// `not`, and therefore, `main` prints `Not-ing!`.
554 ///
555 /// ```
556 /// use std::ops::Not;
557 ///
558 /// struct Foo;
559 ///
560 /// impl Not for Foo {
561 ///     type Output = Foo;
562 ///
563 ///     fn not(self) -> Foo {
564 ///         println!("Not-ing!");
565 ///         self
566 ///     }
567 /// }
568 ///
569 /// fn main() {
570 ///     !Foo;
571 /// }
572 /// ```
573 #[lang = "not"]
574 #[stable(feature = "rust1", since = "1.0.0")]
575 pub trait Not {
576     /// The resulting type after applying the `!` operator
577     #[stable(feature = "rust1", since = "1.0.0")]
578     type Output;
579
580     /// The method for the unary `!` operator
581     #[stable(feature = "rust1", since = "1.0.0")]
582     fn not(self) -> Self::Output;
583 }
584
585 macro_rules! not_impl {
586     ($($t:ty)*) => ($(
587         #[stable(feature = "rust1", since = "1.0.0")]
588         impl Not for $t {
589             type Output = $t;
590
591             #[inline]
592             fn not(self) -> $t { !self }
593         }
594
595         forward_ref_unop! { impl Not, not for $t }
596     )*)
597 }
598
599 not_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
600
601 /// The `BitAnd` trait is used to specify the functionality of `&`.
602 ///
603 /// # Examples
604 ///
605 /// A trivial implementation of `BitAnd`. When `Foo & Foo` happens, it ends up
606 /// calling `bitand`, and therefore, `main` prints `Bitwise And-ing!`.
607 ///
608 /// ```
609 /// use std::ops::BitAnd;
610 ///
611 /// struct Foo;
612 ///
613 /// impl BitAnd for Foo {
614 ///     type Output = Foo;
615 ///
616 ///     fn bitand(self, _rhs: Foo) -> Foo {
617 ///         println!("Bitwise And-ing!");
618 ///         self
619 ///     }
620 /// }
621 ///
622 /// fn main() {
623 ///     Foo & Foo;
624 /// }
625 /// ```
626 #[lang = "bitand"]
627 #[stable(feature = "rust1", since = "1.0.0")]
628 pub trait BitAnd<RHS=Self> {
629     /// The resulting type after applying the `&` operator
630     #[stable(feature = "rust1", since = "1.0.0")]
631     type Output;
632
633     /// The method for the `&` operator
634     #[stable(feature = "rust1", since = "1.0.0")]
635     fn bitand(self, rhs: RHS) -> Self::Output;
636 }
637
638 macro_rules! bitand_impl {
639     ($($t:ty)*) => ($(
640         #[stable(feature = "rust1", since = "1.0.0")]
641         impl BitAnd for $t {
642             type Output = $t;
643
644             #[inline]
645             fn bitand(self, rhs: $t) -> $t { self & rhs }
646         }
647
648         forward_ref_binop! { impl BitAnd, bitand for $t, $t }
649     )*)
650 }
651
652 bitand_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
653
654 /// The `BitOr` trait is used to specify the functionality of `|`.
655 ///
656 /// # Examples
657 ///
658 /// A trivial implementation of `BitOr`. When `Foo | Foo` happens, it ends up
659 /// calling `bitor`, and therefore, `main` prints `Bitwise Or-ing!`.
660 ///
661 /// ```
662 /// use std::ops::BitOr;
663 ///
664 /// struct Foo;
665 ///
666 /// impl BitOr for Foo {
667 ///     type Output = Foo;
668 ///
669 ///     fn bitor(self, _rhs: Foo) -> Foo {
670 ///         println!("Bitwise Or-ing!");
671 ///         self
672 ///     }
673 /// }
674 ///
675 /// fn main() {
676 ///     Foo | Foo;
677 /// }
678 /// ```
679 #[lang = "bitor"]
680 #[stable(feature = "rust1", since = "1.0.0")]
681 pub trait BitOr<RHS=Self> {
682     /// The resulting type after applying the `|` operator
683     #[stable(feature = "rust1", since = "1.0.0")]
684     type Output;
685
686     /// The method for the `|` operator
687     #[stable(feature = "rust1", since = "1.0.0")]
688     fn bitor(self, rhs: RHS) -> Self::Output;
689 }
690
691 macro_rules! bitor_impl {
692     ($($t:ty)*) => ($(
693         #[stable(feature = "rust1", since = "1.0.0")]
694         impl BitOr for $t {
695             type Output = $t;
696
697             #[inline]
698             fn bitor(self, rhs: $t) -> $t { self | rhs }
699         }
700
701         forward_ref_binop! { impl BitOr, bitor for $t, $t }
702     )*)
703 }
704
705 bitor_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
706
707 /// The `BitXor` trait is used to specify the functionality of `^`.
708 ///
709 /// # Examples
710 ///
711 /// A trivial implementation of `BitXor`. When `Foo ^ Foo` happens, it ends up
712 /// calling `bitxor`, and therefore, `main` prints `Bitwise Xor-ing!`.
713 ///
714 /// ```
715 /// use std::ops::BitXor;
716 ///
717 /// struct Foo;
718 ///
719 /// impl BitXor for Foo {
720 ///     type Output = Foo;
721 ///
722 ///     fn bitxor(self, _rhs: Foo) -> Foo {
723 ///         println!("Bitwise Xor-ing!");
724 ///         self
725 ///     }
726 /// }
727 ///
728 /// fn main() {
729 ///     Foo ^ Foo;
730 /// }
731 /// ```
732 #[lang = "bitxor"]
733 #[stable(feature = "rust1", since = "1.0.0")]
734 pub trait BitXor<RHS=Self> {
735     /// The resulting type after applying the `^` operator
736     #[stable(feature = "rust1", since = "1.0.0")]
737     type Output;
738
739     /// The method for the `^` operator
740     #[stable(feature = "rust1", since = "1.0.0")]
741     fn bitxor(self, rhs: RHS) -> Self::Output;
742 }
743
744 macro_rules! bitxor_impl {
745     ($($t:ty)*) => ($(
746         #[stable(feature = "rust1", since = "1.0.0")]
747         impl BitXor for $t {
748             type Output = $t;
749
750             #[inline]
751             fn bitxor(self, other: $t) -> $t { self ^ other }
752         }
753
754         forward_ref_binop! { impl BitXor, bitxor for $t, $t }
755     )*)
756 }
757
758 bitxor_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
759
760 /// The `Shl` trait is used to specify the functionality of `<<`.
761 ///
762 /// # Examples
763 ///
764 /// A trivial implementation of `Shl`. When `Foo << Foo` happens, it ends up
765 /// calling `shl`, and therefore, `main` prints `Shifting left!`.
766 ///
767 /// ```
768 /// use std::ops::Shl;
769 ///
770 /// struct Foo;
771 ///
772 /// impl Shl<Foo> for Foo {
773 ///     type Output = Foo;
774 ///
775 ///     fn shl(self, _rhs: Foo) -> Foo {
776 ///         println!("Shifting left!");
777 ///         self
778 ///     }
779 /// }
780 ///
781 /// fn main() {
782 ///     Foo << Foo;
783 /// }
784 /// ```
785 #[lang = "shl"]
786 #[stable(feature = "rust1", since = "1.0.0")]
787 pub trait Shl<RHS> {
788     /// The resulting type after applying the `<<` operator
789     #[stable(feature = "rust1", since = "1.0.0")]
790     type Output;
791
792     /// The method for the `<<` operator
793     #[stable(feature = "rust1", since = "1.0.0")]
794     fn shl(self, rhs: RHS) -> Self::Output;
795 }
796
797 macro_rules! shl_impl {
798     ($t:ty, $f:ty) => (
799         #[stable(feature = "rust1", since = "1.0.0")]
800         impl Shl<$f> for $t {
801             type Output = $t;
802
803             #[inline]
804             #[rustc_inherit_overflow_checks]
805             fn shl(self, other: $f) -> $t {
806                 self << other
807             }
808         }
809
810         forward_ref_binop! { impl Shl, shl for $t, $f }
811     )
812 }
813
814 macro_rules! shl_impl_all {
815     ($($t:ty)*) => ($(
816         shl_impl! { $t, u8 }
817         shl_impl! { $t, u16 }
818         shl_impl! { $t, u32 }
819         shl_impl! { $t, u64 }
820         shl_impl! { $t, usize }
821
822         shl_impl! { $t, i8 }
823         shl_impl! { $t, i16 }
824         shl_impl! { $t, i32 }
825         shl_impl! { $t, i64 }
826         shl_impl! { $t, isize }
827     )*)
828 }
829
830 shl_impl_all! { u8 u16 u32 u64 usize i8 i16 i32 i64 isize }
831
832 /// The `Shr` trait is used to specify the functionality of `>>`.
833 ///
834 /// # Examples
835 ///
836 /// A trivial implementation of `Shr`. When `Foo >> Foo` happens, it ends up
837 /// calling `shr`, and therefore, `main` prints `Shifting right!`.
838 ///
839 /// ```
840 /// use std::ops::Shr;
841 ///
842 /// struct Foo;
843 ///
844 /// impl Shr<Foo> for Foo {
845 ///     type Output = Foo;
846 ///
847 ///     fn shr(self, _rhs: Foo) -> Foo {
848 ///         println!("Shifting right!");
849 ///         self
850 ///     }
851 /// }
852 ///
853 /// fn main() {
854 ///     Foo >> Foo;
855 /// }
856 /// ```
857 #[lang = "shr"]
858 #[stable(feature = "rust1", since = "1.0.0")]
859 pub trait Shr<RHS> {
860     /// The resulting type after applying the `>>` operator
861     #[stable(feature = "rust1", since = "1.0.0")]
862     type Output;
863
864     /// The method for the `>>` operator
865     #[stable(feature = "rust1", since = "1.0.0")]
866     fn shr(self, rhs: RHS) -> Self::Output;
867 }
868
869 macro_rules! shr_impl {
870     ($t:ty, $f:ty) => (
871         #[stable(feature = "rust1", since = "1.0.0")]
872         impl Shr<$f> for $t {
873             type Output = $t;
874
875             #[inline]
876             #[rustc_inherit_overflow_checks]
877             fn shr(self, other: $f) -> $t {
878                 self >> other
879             }
880         }
881
882         forward_ref_binop! { impl Shr, shr for $t, $f }
883     )
884 }
885
886 macro_rules! shr_impl_all {
887     ($($t:ty)*) => ($(
888         shr_impl! { $t, u8 }
889         shr_impl! { $t, u16 }
890         shr_impl! { $t, u32 }
891         shr_impl! { $t, u64 }
892         shr_impl! { $t, usize }
893
894         shr_impl! { $t, i8 }
895         shr_impl! { $t, i16 }
896         shr_impl! { $t, i32 }
897         shr_impl! { $t, i64 }
898         shr_impl! { $t, isize }
899     )*)
900 }
901
902 shr_impl_all! { u8 u16 u32 u64 usize i8 i16 i32 i64 isize }
903
904 /// The `AddAssign` trait is used to specify the functionality of `+=`.
905 ///
906 /// # Examples
907 ///
908 /// A trivial implementation of `AddAssign`. When `Foo += Foo` happens, it ends up
909 /// calling `add_assign`, and therefore, `main` prints `Adding!`.
910 ///
911 /// ```
912 /// use std::ops::AddAssign;
913 ///
914 /// struct Foo;
915 ///
916 /// impl AddAssign for Foo {
917 ///     fn add_assign(&mut self, _rhs: Foo) {
918 ///         println!("Adding!");
919 ///     }
920 /// }
921 ///
922 /// # #[allow(unused_assignments)]
923 /// fn main() {
924 ///     let mut foo = Foo;
925 ///     foo += Foo;
926 /// }
927 /// ```
928 #[lang = "add_assign"]
929 #[stable(feature = "op_assign_traits", since = "1.8.0")]
930 pub trait AddAssign<Rhs=Self> {
931     /// The method for the `+=` operator
932     #[stable(feature = "op_assign_traits", since = "1.8.0")]
933     fn add_assign(&mut self, Rhs);
934 }
935
936 macro_rules! add_assign_impl {
937     ($($t:ty)+) => ($(
938         #[stable(feature = "op_assign_traits", since = "1.8.0")]
939         impl AddAssign for $t {
940             #[inline]
941             #[rustc_inherit_overflow_checks]
942             fn add_assign(&mut self, other: $t) { *self += other }
943         }
944     )+)
945 }
946
947 add_assign_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
948
949 /// The `SubAssign` trait is used to specify the functionality of `-=`.
950 ///
951 /// # Examples
952 ///
953 /// A trivial implementation of `SubAssign`. When `Foo -= Foo` happens, it ends up
954 /// calling `sub_assign`, and therefore, `main` prints `Subtracting!`.
955 ///
956 /// ```
957 /// use std::ops::SubAssign;
958 ///
959 /// struct Foo;
960 ///
961 /// impl SubAssign for Foo {
962 ///     fn sub_assign(&mut self, _rhs: Foo) {
963 ///         println!("Subtracting!");
964 ///     }
965 /// }
966 ///
967 /// # #[allow(unused_assignments)]
968 /// fn main() {
969 ///     let mut foo = Foo;
970 ///     foo -= Foo;
971 /// }
972 /// ```
973 #[lang = "sub_assign"]
974 #[stable(feature = "op_assign_traits", since = "1.8.0")]
975 pub trait SubAssign<Rhs=Self> {
976     /// The method for the `-=` operator
977     #[stable(feature = "op_assign_traits", since = "1.8.0")]
978     fn sub_assign(&mut self, Rhs);
979 }
980
981 macro_rules! sub_assign_impl {
982     ($($t:ty)+) => ($(
983         #[stable(feature = "op_assign_traits", since = "1.8.0")]
984         impl SubAssign for $t {
985             #[inline]
986             #[rustc_inherit_overflow_checks]
987             fn sub_assign(&mut self, other: $t) { *self -= other }
988         }
989     )+)
990 }
991
992 sub_assign_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
993
994 /// The `MulAssign` trait is used to specify the functionality of `*=`.
995 ///
996 /// # Examples
997 ///
998 /// A trivial implementation of `MulAssign`. When `Foo *= Foo` happens, it ends up
999 /// calling `mul_assign`, and therefore, `main` prints `Multiplying!`.
1000 ///
1001 /// ```
1002 /// use std::ops::MulAssign;
1003 ///
1004 /// struct Foo;
1005 ///
1006 /// impl MulAssign for Foo {
1007 ///     fn mul_assign(&mut self, _rhs: Foo) {
1008 ///         println!("Multiplying!");
1009 ///     }
1010 /// }
1011 ///
1012 /// # #[allow(unused_assignments)]
1013 /// fn main() {
1014 ///     let mut foo = Foo;
1015 ///     foo *= Foo;
1016 /// }
1017 /// ```
1018 #[lang = "mul_assign"]
1019 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1020 pub trait MulAssign<Rhs=Self> {
1021     /// The method for the `*=` operator
1022     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1023     fn mul_assign(&mut self, Rhs);
1024 }
1025
1026 macro_rules! mul_assign_impl {
1027     ($($t:ty)+) => ($(
1028         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1029         impl MulAssign for $t {
1030             #[inline]
1031             #[rustc_inherit_overflow_checks]
1032             fn mul_assign(&mut self, other: $t) { *self *= other }
1033         }
1034     )+)
1035 }
1036
1037 mul_assign_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
1038
1039 /// The `DivAssign` trait is used to specify the functionality of `/=`.
1040 ///
1041 /// # Examples
1042 ///
1043 /// A trivial implementation of `DivAssign`. When `Foo /= Foo` happens, it ends up
1044 /// calling `div_assign`, and therefore, `main` prints `Dividing!`.
1045 ///
1046 /// ```
1047 /// use std::ops::DivAssign;
1048 ///
1049 /// struct Foo;
1050 ///
1051 /// impl DivAssign for Foo {
1052 ///     fn div_assign(&mut self, _rhs: Foo) {
1053 ///         println!("Dividing!");
1054 ///     }
1055 /// }
1056 ///
1057 /// # #[allow(unused_assignments)]
1058 /// fn main() {
1059 ///     let mut foo = Foo;
1060 ///     foo /= Foo;
1061 /// }
1062 /// ```
1063 #[lang = "div_assign"]
1064 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1065 pub trait DivAssign<Rhs=Self> {
1066     /// The method for the `/=` operator
1067     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1068     fn div_assign(&mut self, Rhs);
1069 }
1070
1071 macro_rules! div_assign_impl {
1072     ($($t:ty)+) => ($(
1073         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1074         impl DivAssign for $t {
1075             #[inline]
1076             fn div_assign(&mut self, other: $t) { *self /= other }
1077         }
1078     )+)
1079 }
1080
1081 div_assign_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
1082
1083 /// The `RemAssign` trait is used to specify the functionality of `%=`.
1084 ///
1085 /// # Examples
1086 ///
1087 /// A trivial implementation of `RemAssign`. When `Foo %= Foo` happens, it ends up
1088 /// calling `rem_assign`, and therefore, `main` prints `Remainder-ing!`.
1089 ///
1090 /// ```
1091 /// use std::ops::RemAssign;
1092 ///
1093 /// struct Foo;
1094 ///
1095 /// impl RemAssign for Foo {
1096 ///     fn rem_assign(&mut self, _rhs: Foo) {
1097 ///         println!("Remainder-ing!");
1098 ///     }
1099 /// }
1100 ///
1101 /// # #[allow(unused_assignments)]
1102 /// fn main() {
1103 ///     let mut foo = Foo;
1104 ///     foo %= Foo;
1105 /// }
1106 /// ```
1107 #[lang = "rem_assign"]
1108 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1109 pub trait RemAssign<Rhs=Self> {
1110     /// The method for the `%=` operator
1111     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1112     fn rem_assign(&mut self, Rhs);
1113 }
1114
1115 macro_rules! rem_assign_impl {
1116     ($($t:ty)+) => ($(
1117         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1118         impl RemAssign for $t {
1119             #[inline]
1120             fn rem_assign(&mut self, other: $t) { *self %= other }
1121         }
1122     )+)
1123 }
1124
1125 rem_assign_impl! { usize u8 u16 u32 u64 isize i8 i16 i32 i64 f32 f64 }
1126
1127 /// The `BitAndAssign` trait is used to specify the functionality of `&=`.
1128 ///
1129 /// # Examples
1130 ///
1131 /// A trivial implementation of `BitAndAssign`. When `Foo &= Foo` happens, it ends up
1132 /// calling `bitand_assign`, and therefore, `main` prints `Bitwise And-ing!`.
1133 ///
1134 /// ```
1135 /// use std::ops::BitAndAssign;
1136 ///
1137 /// struct Foo;
1138 ///
1139 /// impl BitAndAssign for Foo {
1140 ///     fn bitand_assign(&mut self, _rhs: Foo) {
1141 ///         println!("Bitwise And-ing!");
1142 ///     }
1143 /// }
1144 ///
1145 /// # #[allow(unused_assignments)]
1146 /// fn main() {
1147 ///     let mut foo = Foo;
1148 ///     foo &= Foo;
1149 /// }
1150 /// ```
1151 #[lang = "bitand_assign"]
1152 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1153 pub trait BitAndAssign<Rhs=Self> {
1154     /// The method for the `&` operator
1155     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1156     fn bitand_assign(&mut self, Rhs);
1157 }
1158
1159 macro_rules! bitand_assign_impl {
1160     ($($t:ty)+) => ($(
1161         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1162         impl BitAndAssign for $t {
1163             #[inline]
1164             fn bitand_assign(&mut self, other: $t) { *self &= other }
1165         }
1166     )+)
1167 }
1168
1169 bitand_assign_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
1170
1171 /// The `BitOrAssign` trait is used to specify the functionality of `|=`.
1172 ///
1173 /// # Examples
1174 ///
1175 /// A trivial implementation of `BitOrAssign`. When `Foo |= Foo` happens, it ends up
1176 /// calling `bitor_assign`, and therefore, `main` prints `Bitwise Or-ing!`.
1177 ///
1178 /// ```
1179 /// use std::ops::BitOrAssign;
1180 ///
1181 /// struct Foo;
1182 ///
1183 /// impl BitOrAssign for Foo {
1184 ///     fn bitor_assign(&mut self, _rhs: Foo) {
1185 ///         println!("Bitwise Or-ing!");
1186 ///     }
1187 /// }
1188 ///
1189 /// # #[allow(unused_assignments)]
1190 /// fn main() {
1191 ///     let mut foo = Foo;
1192 ///     foo |= Foo;
1193 /// }
1194 /// ```
1195 #[lang = "bitor_assign"]
1196 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1197 pub trait BitOrAssign<Rhs=Self> {
1198     /// The method for the `|=` operator
1199     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1200     fn bitor_assign(&mut self, Rhs);
1201 }
1202
1203 macro_rules! bitor_assign_impl {
1204     ($($t:ty)+) => ($(
1205         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1206         impl BitOrAssign for $t {
1207             #[inline]
1208             fn bitor_assign(&mut self, other: $t) { *self |= other }
1209         }
1210     )+)
1211 }
1212
1213 bitor_assign_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
1214
1215 /// The `BitXorAssign` trait is used to specify the functionality of `^=`.
1216 ///
1217 /// # Examples
1218 ///
1219 /// A trivial implementation of `BitXorAssign`. When `Foo ^= Foo` happens, it ends up
1220 /// calling `bitxor_assign`, and therefore, `main` prints `Bitwise Xor-ing!`.
1221 ///
1222 /// ```
1223 /// use std::ops::BitXorAssign;
1224 ///
1225 /// struct Foo;
1226 ///
1227 /// impl BitXorAssign for Foo {
1228 ///     fn bitxor_assign(&mut self, _rhs: Foo) {
1229 ///         println!("Bitwise Xor-ing!");
1230 ///     }
1231 /// }
1232 ///
1233 /// # #[allow(unused_assignments)]
1234 /// fn main() {
1235 ///     let mut foo = Foo;
1236 ///     foo ^= Foo;
1237 /// }
1238 /// ```
1239 #[lang = "bitxor_assign"]
1240 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1241 pub trait BitXorAssign<Rhs=Self> {
1242     /// The method for the `^=` operator
1243     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1244     fn bitxor_assign(&mut self, Rhs);
1245 }
1246
1247 macro_rules! bitxor_assign_impl {
1248     ($($t:ty)+) => ($(
1249         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1250         impl BitXorAssign for $t {
1251             #[inline]
1252             fn bitxor_assign(&mut self, other: $t) { *self ^= other }
1253         }
1254     )+)
1255 }
1256
1257 bitxor_assign_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
1258
1259 /// The `ShlAssign` trait is used to specify the functionality of `<<=`.
1260 ///
1261 /// # Examples
1262 ///
1263 /// A trivial implementation of `ShlAssign`. When `Foo <<= Foo` happens, it ends up
1264 /// calling `shl_assign`, and therefore, `main` prints `Shifting left!`.
1265 ///
1266 /// ```
1267 /// use std::ops::ShlAssign;
1268 ///
1269 /// struct Foo;
1270 ///
1271 /// impl ShlAssign<Foo> for Foo {
1272 ///     fn shl_assign(&mut self, _rhs: Foo) {
1273 ///         println!("Shifting left!");
1274 ///     }
1275 /// }
1276 ///
1277 /// # #[allow(unused_assignments)]
1278 /// fn main() {
1279 ///     let mut foo = Foo;
1280 ///     foo <<= Foo;
1281 /// }
1282 /// ```
1283 #[lang = "shl_assign"]
1284 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1285 pub trait ShlAssign<Rhs> {
1286     /// The method for the `<<=` operator
1287     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1288     fn shl_assign(&mut self, Rhs);
1289 }
1290
1291 macro_rules! shl_assign_impl {
1292     ($t:ty, $f:ty) => (
1293         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1294         impl ShlAssign<$f> for $t {
1295             #[inline]
1296             #[rustc_inherit_overflow_checks]
1297             fn shl_assign(&mut self, other: $f) {
1298                 *self <<= other
1299             }
1300         }
1301     )
1302 }
1303
1304 macro_rules! shl_assign_impl_all {
1305     ($($t:ty)*) => ($(
1306         shl_assign_impl! { $t, u8 }
1307         shl_assign_impl! { $t, u16 }
1308         shl_assign_impl! { $t, u32 }
1309         shl_assign_impl! { $t, u64 }
1310         shl_assign_impl! { $t, usize }
1311
1312         shl_assign_impl! { $t, i8 }
1313         shl_assign_impl! { $t, i16 }
1314         shl_assign_impl! { $t, i32 }
1315         shl_assign_impl! { $t, i64 }
1316         shl_assign_impl! { $t, isize }
1317     )*)
1318 }
1319
1320 shl_assign_impl_all! { u8 u16 u32 u64 usize i8 i16 i32 i64 isize }
1321
1322 /// The `ShrAssign` trait is used to specify the functionality of `>>=`.
1323 ///
1324 /// # Examples
1325 ///
1326 /// A trivial implementation of `ShrAssign`. When `Foo >>= Foo` happens, it ends up
1327 /// calling `shr_assign`, and therefore, `main` prints `Shifting right!`.
1328 ///
1329 /// ```
1330 /// use std::ops::ShrAssign;
1331 ///
1332 /// struct Foo;
1333 ///
1334 /// impl ShrAssign<Foo> for Foo {
1335 ///     fn shr_assign(&mut self, _rhs: Foo) {
1336 ///         println!("Shifting right!");
1337 ///     }
1338 /// }
1339 ///
1340 /// # #[allow(unused_assignments)]
1341 /// fn main() {
1342 ///     let mut foo = Foo;
1343 ///     foo >>= Foo;
1344 /// }
1345 /// ```
1346 #[lang = "shr_assign"]
1347 #[stable(feature = "op_assign_traits", since = "1.8.0")]
1348 pub trait ShrAssign<Rhs=Self> {
1349     /// The method for the `>>=` operator
1350     #[stable(feature = "op_assign_traits", since = "1.8.0")]
1351     fn shr_assign(&mut self, Rhs);
1352 }
1353
1354 macro_rules! shr_assign_impl {
1355     ($t:ty, $f:ty) => (
1356         #[stable(feature = "op_assign_traits", since = "1.8.0")]
1357         impl ShrAssign<$f> for $t {
1358             #[inline]
1359             #[rustc_inherit_overflow_checks]
1360             fn shr_assign(&mut self, other: $f) {
1361                 *self >>= other
1362             }
1363         }
1364     )
1365 }
1366
1367 macro_rules! shr_assign_impl_all {
1368     ($($t:ty)*) => ($(
1369         shr_assign_impl! { $t, u8 }
1370         shr_assign_impl! { $t, u16 }
1371         shr_assign_impl! { $t, u32 }
1372         shr_assign_impl! { $t, u64 }
1373         shr_assign_impl! { $t, usize }
1374
1375         shr_assign_impl! { $t, i8 }
1376         shr_assign_impl! { $t, i16 }
1377         shr_assign_impl! { $t, i32 }
1378         shr_assign_impl! { $t, i64 }
1379         shr_assign_impl! { $t, isize }
1380     )*)
1381 }
1382
1383 shr_assign_impl_all! { u8 u16 u32 u64 usize i8 i16 i32 i64 isize }
1384
1385 /// The `Index` trait is used to specify the functionality of indexing operations
1386 /// like `arr[idx]` when used in an immutable context.
1387 ///
1388 /// # Examples
1389 ///
1390 /// A trivial implementation of `Index`. When `Foo[Bar]` happens, it ends up
1391 /// calling `index`, and therefore, `main` prints `Indexing!`.
1392 ///
1393 /// ```
1394 /// use std::ops::Index;
1395 ///
1396 /// #[derive(Copy, Clone)]
1397 /// struct Foo;
1398 /// struct Bar;
1399 ///
1400 /// impl Index<Bar> for Foo {
1401 ///     type Output = Foo;
1402 ///
1403 ///     fn index<'a>(&'a self, _index: Bar) -> &'a Foo {
1404 ///         println!("Indexing!");
1405 ///         self
1406 ///     }
1407 /// }
1408 ///
1409 /// fn main() {
1410 ///     Foo[Bar];
1411 /// }
1412 /// ```
1413 #[lang = "index"]
1414 #[rustc_on_unimplemented = "the type `{Self}` cannot be indexed by `{Idx}`"]
1415 #[stable(feature = "rust1", since = "1.0.0")]
1416 pub trait Index<Idx: ?Sized> {
1417     /// The returned type after indexing
1418     #[stable(feature = "rust1", since = "1.0.0")]
1419     type Output: ?Sized;
1420
1421     /// The method for the indexing (`Foo[Bar]`) operation
1422     #[stable(feature = "rust1", since = "1.0.0")]
1423     fn index(&self, index: Idx) -> &Self::Output;
1424 }
1425
1426 /// The `IndexMut` trait is used to specify the functionality of indexing
1427 /// operations like `arr[idx]`, when used in a mutable context.
1428 ///
1429 /// # Examples
1430 ///
1431 /// A trivial implementation of `IndexMut`. When `Foo[Bar]` happens, it ends up
1432 /// calling `index_mut`, and therefore, `main` prints `Indexing!`.
1433 ///
1434 /// ```
1435 /// use std::ops::{Index, IndexMut};
1436 ///
1437 /// #[derive(Copy, Clone)]
1438 /// struct Foo;
1439 /// struct Bar;
1440 ///
1441 /// impl Index<Bar> for Foo {
1442 ///     type Output = Foo;
1443 ///
1444 ///     fn index<'a>(&'a self, _index: Bar) -> &'a Foo {
1445 ///         self
1446 ///     }
1447 /// }
1448 ///
1449 /// impl IndexMut<Bar> for Foo {
1450 ///     fn index_mut<'a>(&'a mut self, _index: Bar) -> &'a mut Foo {
1451 ///         println!("Indexing!");
1452 ///         self
1453 ///     }
1454 /// }
1455 ///
1456 /// fn main() {
1457 ///     &mut Foo[Bar];
1458 /// }
1459 /// ```
1460 #[lang = "index_mut"]
1461 #[rustc_on_unimplemented = "the type `{Self}` cannot be mutably indexed by `{Idx}`"]
1462 #[stable(feature = "rust1", since = "1.0.0")]
1463 pub trait IndexMut<Idx: ?Sized>: Index<Idx> {
1464     /// The method for the indexing (`Foo[Bar]`) operation
1465     #[stable(feature = "rust1", since = "1.0.0")]
1466     fn index_mut(&mut self, index: Idx) -> &mut Self::Output;
1467 }
1468
1469 /// An unbounded range. Use `..` (two dots) for its shorthand.
1470 ///
1471 /// Its primary use case is slicing index. It cannot serve as an iterator
1472 /// because it doesn't have a starting point.
1473 ///
1474 /// # Examples
1475 ///
1476 /// ```
1477 /// fn main() {
1478 ///     assert_eq!((..), std::ops::RangeFull);
1479 ///
1480 ///     let arr = [0, 1, 2, 3];
1481 ///     assert_eq!(arr[ .. ], [0,1,2,3]);  // RangeFull
1482 ///     assert_eq!(arr[ ..3], [0,1,2  ]);
1483 ///     assert_eq!(arr[1.. ], [  1,2,3]);
1484 ///     assert_eq!(arr[1..3], [  1,2  ]);
1485 /// }
1486 /// ```
1487 #[derive(Copy, Clone, PartialEq, Eq, Hash)]
1488 #[stable(feature = "rust1", since = "1.0.0")]
1489 pub struct RangeFull;
1490
1491 #[stable(feature = "rust1", since = "1.0.0")]
1492 impl fmt::Debug for RangeFull {
1493     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1494         write!(fmt, "..")
1495     }
1496 }
1497
1498 /// A (half-open) range which is bounded at both ends: { x | start <= x < end }.
1499 /// Use `start..end` (two dots) for its shorthand.
1500 ///
1501 /// See the [`contains()`](#method.contains) method for its characterization.
1502 ///
1503 /// # Examples
1504 ///
1505 /// ```
1506 /// fn main() {
1507 ///     assert_eq!((3..5), std::ops::Range{ start: 3, end: 5 });
1508 ///     assert_eq!(3+4+5, (3..6).sum());
1509 ///
1510 ///     let arr = [0, 1, 2, 3];
1511 ///     assert_eq!(arr[ .. ], [0,1,2,3]);
1512 ///     assert_eq!(arr[ ..3], [0,1,2  ]);
1513 ///     assert_eq!(arr[1.. ], [  1,2,3]);
1514 ///     assert_eq!(arr[1..3], [  1,2  ]);  // Range
1515 /// }
1516 /// ```
1517 #[derive(Clone, PartialEq, Eq, Hash)]  // not Copy -- see #27186
1518 #[stable(feature = "rust1", since = "1.0.0")]
1519 pub struct Range<Idx> {
1520     /// The lower bound of the range (inclusive).
1521     #[stable(feature = "rust1", since = "1.0.0")]
1522     pub start: Idx,
1523     /// The upper bound of the range (exclusive).
1524     #[stable(feature = "rust1", since = "1.0.0")]
1525     pub end: Idx,
1526 }
1527
1528 #[stable(feature = "rust1", since = "1.0.0")]
1529 impl<Idx: fmt::Debug> fmt::Debug for Range<Idx> {
1530     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1531         write!(fmt, "{:?}..{:?}", self.start, self.end)
1532     }
1533 }
1534
1535 #[unstable(feature = "range_contains", reason = "recently added as per RFC", issue = "32311")]
1536 impl<Idx: PartialOrd<Idx>> Range<Idx> {
1537     /// # Examples
1538     ///
1539     /// ```
1540     /// #![feature(range_contains)]
1541     /// fn main() {
1542     ///     assert!( ! (3..5).contains(2));
1543     ///     assert!(   (3..5).contains(3));
1544     ///     assert!(   (3..5).contains(4));
1545     ///     assert!( ! (3..5).contains(5));
1546     ///
1547     ///     assert!( ! (3..3).contains(3));
1548     ///     assert!( ! (3..2).contains(3));
1549     /// }
1550     /// ```
1551     pub fn contains(&self, item: Idx) -> bool {
1552         (self.start <= item) && (item < self.end)
1553     }
1554 }
1555
1556 /// A range which is only bounded below: { x | start <= x }.
1557 /// Use `start..` for its shorthand.
1558 ///
1559 /// See the [`contains()`](#method.contains) method for its characterization.
1560 ///
1561 /// Note: Currently, no overflow checking is done for the iterator
1562 /// implementation; if you use an integer range and the integer overflows, it
1563 /// might panic in debug mode or create an endless loop in release mode. This
1564 /// overflow behavior might change in the future.
1565 ///
1566 /// # Examples
1567 ///
1568 /// ```
1569 /// fn main() {
1570 ///     assert_eq!((2..), std::ops::RangeFrom{ start: 2 });
1571 ///     assert_eq!(2+3+4, (2..).take(3).sum());
1572 ///
1573 ///     let arr = [0, 1, 2, 3];
1574 ///     assert_eq!(arr[ .. ], [0,1,2,3]);
1575 ///     assert_eq!(arr[ ..3], [0,1,2  ]);
1576 ///     assert_eq!(arr[1.. ], [  1,2,3]);  // RangeFrom
1577 ///     assert_eq!(arr[1..3], [  1,2  ]);
1578 /// }
1579 /// ```
1580 #[derive(Clone, PartialEq, Eq, Hash)]  // not Copy -- see #27186
1581 #[stable(feature = "rust1", since = "1.0.0")]
1582 pub struct RangeFrom<Idx> {
1583     /// The lower bound of the range (inclusive).
1584     #[stable(feature = "rust1", since = "1.0.0")]
1585     pub start: Idx,
1586 }
1587
1588 #[stable(feature = "rust1", since = "1.0.0")]
1589 impl<Idx: fmt::Debug> fmt::Debug for RangeFrom<Idx> {
1590     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1591         write!(fmt, "{:?}..", self.start)
1592     }
1593 }
1594
1595 #[unstable(feature = "range_contains", reason = "recently added as per RFC", issue = "32311")]
1596 impl<Idx: PartialOrd<Idx>> RangeFrom<Idx> {
1597     /// # Examples
1598     ///
1599     /// ```
1600     /// #![feature(range_contains)]
1601     /// fn main() {
1602     ///     assert!( ! (3..).contains(2));
1603     ///     assert!(   (3..).contains(3));
1604     ///     assert!(   (3..).contains(1_000_000_000));
1605     /// }
1606     /// ```
1607     pub fn contains(&self, item: Idx) -> bool {
1608         (self.start <= item)
1609     }
1610 }
1611
1612 /// A range which is only bounded above: { x | x < end }.
1613 /// Use `..end` (two dots) for its shorthand.
1614 ///
1615 /// See the [`contains()`](#method.contains) method for its characterization.
1616 ///
1617 /// It cannot serve as an iterator because it doesn't have a starting point.
1618 ///
1619 /// ```
1620 /// fn main() {
1621 ///     assert_eq!((..5), std::ops::RangeTo{ end: 5 });
1622 ///
1623 ///     let arr = [0, 1, 2, 3];
1624 ///     assert_eq!(arr[ .. ], [0,1,2,3]);
1625 ///     assert_eq!(arr[ ..3], [0,1,2  ]);  // RangeTo
1626 ///     assert_eq!(arr[1.. ], [  1,2,3]);
1627 ///     assert_eq!(arr[1..3], [  1,2  ]);
1628 /// }
1629 /// ```
1630 #[derive(Copy, Clone, PartialEq, Eq, Hash)]
1631 #[stable(feature = "rust1", since = "1.0.0")]
1632 pub struct RangeTo<Idx> {
1633     /// The upper bound of the range (exclusive).
1634     #[stable(feature = "rust1", since = "1.0.0")]
1635     pub end: Idx,
1636 }
1637
1638 #[stable(feature = "rust1", since = "1.0.0")]
1639 impl<Idx: fmt::Debug> fmt::Debug for RangeTo<Idx> {
1640     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1641         write!(fmt, "..{:?}", self.end)
1642     }
1643 }
1644
1645 #[unstable(feature = "range_contains", reason = "recently added as per RFC", issue = "32311")]
1646 impl<Idx: PartialOrd<Idx>> RangeTo<Idx> {
1647     /// # Examples
1648     ///
1649     /// ```
1650     /// #![feature(range_contains)]
1651     /// fn main() {
1652     ///     assert!(   (..5).contains(-1_000_000_000));
1653     ///     assert!(   (..5).contains(4));
1654     ///     assert!( ! (..5).contains(5));
1655     /// }
1656     /// ```
1657     pub fn contains(&self, item: Idx) -> bool {
1658         (item < self.end)
1659     }
1660 }
1661
1662 /// An inclusive range which is bounded at both ends: { x | start <= x <= end }.
1663 /// Use `start...end` (three dots) for its shorthand.
1664 ///
1665 /// See the [`contains()`](#method.contains) method for its characterization.
1666 ///
1667 /// # Examples
1668 ///
1669 /// ```
1670 /// #![feature(inclusive_range,inclusive_range_syntax)]
1671 /// fn main() {
1672 ///     assert_eq!((3...5), std::ops::RangeInclusive::NonEmpty{ start: 3, end: 5 });
1673 ///     assert_eq!(3+4+5, (3...5).sum());
1674 ///
1675 ///     let arr = [0, 1, 2, 3];
1676 ///     assert_eq!(arr[ ...2], [0,1,2  ]);
1677 ///     assert_eq!(arr[1...2], [  1,2  ]);  // RangeInclusive
1678 /// }
1679 /// ```
1680 #[derive(Clone, PartialEq, Eq, Hash)]  // not Copy -- see #27186
1681 #[unstable(feature = "inclusive_range", reason = "recently added, follows RFC", issue = "28237")]
1682 pub enum RangeInclusive<Idx> {
1683     /// Empty range (iteration has finished)
1684     #[unstable(feature = "inclusive_range",
1685                reason = "recently added, follows RFC",
1686                issue = "28237")]
1687     Empty {
1688         /// The point at which iteration finished
1689         #[unstable(feature = "inclusive_range",
1690                    reason = "recently added, follows RFC",
1691                    issue = "28237")]
1692         at: Idx
1693     },
1694     /// Non-empty range (iteration will yield value(s))
1695     #[unstable(feature = "inclusive_range",
1696                reason = "recently added, follows RFC",
1697                issue = "28237")]
1698     NonEmpty {
1699         /// The lower bound of the range (inclusive).
1700         #[unstable(feature = "inclusive_range",
1701                    reason = "recently added, follows RFC",
1702                    issue = "28237")]
1703         start: Idx,
1704         /// The upper bound of the range (inclusive).
1705         #[unstable(feature = "inclusive_range",
1706                    reason = "recently added, follows RFC",
1707                    issue = "28237")]
1708         end: Idx,
1709     },
1710 }
1711
1712 #[unstable(feature = "inclusive_range", reason = "recently added, follows RFC", issue = "28237")]
1713 impl<Idx: fmt::Debug> fmt::Debug for RangeInclusive<Idx> {
1714     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1715         use self::RangeInclusive::*;
1716
1717         match *self {
1718             Empty { ref at } => write!(fmt, "[empty range @ {:?}]", at),
1719             NonEmpty { ref start, ref end } => write!(fmt, "{:?}...{:?}", start, end),
1720         }
1721     }
1722 }
1723
1724 #[unstable(feature = "range_contains", reason = "recently added as per RFC", issue = "32311")]
1725 impl<Idx: PartialOrd<Idx>> RangeInclusive<Idx> {
1726     /// # Examples
1727     ///
1728     /// ```
1729     /// #![feature(range_contains,inclusive_range_syntax)]
1730     /// fn main() {
1731     ///     assert!( ! (3...5).contains(2));
1732     ///     assert!(   (3...5).contains(3));
1733     ///     assert!(   (3...5).contains(4));
1734     ///     assert!(   (3...5).contains(5));
1735     ///     assert!( ! (3...5).contains(6));
1736     ///
1737     ///     assert!(   (3...3).contains(3));
1738     ///     assert!( ! (3...2).contains(3));
1739     /// }
1740     /// ```
1741     pub fn contains(&self, item: Idx) -> bool {
1742         if let &RangeInclusive::NonEmpty{ref start, ref end} = self {
1743             (*start <= item) && (item <= *end)
1744         } else { false }
1745     }
1746 }
1747
1748 /// An inclusive range which is only bounded above: { x | x <= end }.
1749 /// Use `...end` (three dots) for its shorthand.
1750 ///
1751 /// See the [`contains()`](#method.contains) method for its characterization.
1752 ///
1753 /// It cannot serve as an iterator because it doesn't have a starting point.
1754 ///
1755 /// # Examples
1756 ///
1757 /// ```
1758 /// #![feature(inclusive_range,inclusive_range_syntax)]
1759 /// fn main() {
1760 ///     assert_eq!((...5), std::ops::RangeToInclusive{ end: 5 });
1761 ///
1762 ///     let arr = [0, 1, 2, 3];
1763 ///     assert_eq!(arr[ ...2], [0,1,2  ]);  // RangeToInclusive
1764 ///     assert_eq!(arr[1...2], [  1,2  ]);
1765 /// }
1766 /// ```
1767 #[derive(Copy, Clone, PartialEq, Eq, Hash)]
1768 #[unstable(feature = "inclusive_range", reason = "recently added, follows RFC", issue = "28237")]
1769 pub struct RangeToInclusive<Idx> {
1770     /// The upper bound of the range (inclusive)
1771     #[unstable(feature = "inclusive_range",
1772                reason = "recently added, follows RFC",
1773                issue = "28237")]
1774     pub end: Idx,
1775 }
1776
1777 #[unstable(feature = "inclusive_range", reason = "recently added, follows RFC", issue = "28237")]
1778 impl<Idx: fmt::Debug> fmt::Debug for RangeToInclusive<Idx> {
1779     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
1780         write!(fmt, "...{:?}", self.end)
1781     }
1782 }
1783
1784 #[unstable(feature = "range_contains", reason = "recently added as per RFC", issue = "32311")]
1785 impl<Idx: PartialOrd<Idx>> RangeToInclusive<Idx> {
1786     /// # Examples
1787     ///
1788     /// ```
1789     /// #![feature(range_contains,inclusive_range_syntax)]
1790     /// fn main() {
1791     ///     assert!(   (...5).contains(-1_000_000_000));
1792     ///     assert!(   (...5).contains(5));
1793     ///     assert!( ! (...5).contains(6));
1794     /// }
1795     /// ```
1796     pub fn contains(&self, item: Idx) -> bool {
1797         (item <= self.end)
1798     }
1799 }
1800
1801 // RangeToInclusive<Idx> cannot impl From<RangeTo<Idx>>
1802 // because underflow would be possible with (..0).into()
1803
1804 /// The `Deref` trait is used to specify the functionality of dereferencing
1805 /// operations, like `*v`.
1806 ///
1807 /// `Deref` also enables ['`Deref` coercions'][coercions].
1808 ///
1809 /// [coercions]: ../../book/deref-coercions.html
1810 ///
1811 /// # Examples
1812 ///
1813 /// A struct with a single field which is accessible via dereferencing the
1814 /// struct.
1815 ///
1816 /// ```
1817 /// use std::ops::Deref;
1818 ///
1819 /// struct DerefExample<T> {
1820 ///     value: T
1821 /// }
1822 ///
1823 /// impl<T> Deref for DerefExample<T> {
1824 ///     type Target = T;
1825 ///
1826 ///     fn deref(&self) -> &T {
1827 ///         &self.value
1828 ///     }
1829 /// }
1830 ///
1831 /// fn main() {
1832 ///     let x = DerefExample { value: 'a' };
1833 ///     assert_eq!('a', *x);
1834 /// }
1835 /// ```
1836 #[lang = "deref"]
1837 #[stable(feature = "rust1", since = "1.0.0")]
1838 pub trait Deref {
1839     /// The resulting type after dereferencing
1840     #[stable(feature = "rust1", since = "1.0.0")]
1841     type Target: ?Sized;
1842
1843     /// The method called to dereference a value
1844     #[stable(feature = "rust1", since = "1.0.0")]
1845     fn deref(&self) -> &Self::Target;
1846 }
1847
1848 #[stable(feature = "rust1", since = "1.0.0")]
1849 impl<'a, T: ?Sized> Deref for &'a T {
1850     type Target = T;
1851
1852     fn deref(&self) -> &T { *self }
1853 }
1854
1855 #[stable(feature = "rust1", since = "1.0.0")]
1856 impl<'a, T: ?Sized> Deref for &'a mut T {
1857     type Target = T;
1858
1859     fn deref(&self) -> &T { *self }
1860 }
1861
1862 /// The `DerefMut` trait is used to specify the functionality of dereferencing
1863 /// mutably like `*v = 1;`
1864 ///
1865 /// `DerefMut` also enables ['`Deref` coercions'][coercions].
1866 ///
1867 /// [coercions]: ../../book/deref-coercions.html
1868 ///
1869 /// # Examples
1870 ///
1871 /// A struct with a single field which is modifiable via dereferencing the
1872 /// struct.
1873 ///
1874 /// ```
1875 /// use std::ops::{Deref, DerefMut};
1876 ///
1877 /// struct DerefMutExample<T> {
1878 ///     value: T
1879 /// }
1880 ///
1881 /// impl<T> Deref for DerefMutExample<T> {
1882 ///     type Target = T;
1883 ///
1884 ///     fn deref<'a>(&'a self) -> &'a T {
1885 ///         &self.value
1886 ///     }
1887 /// }
1888 ///
1889 /// impl<T> DerefMut for DerefMutExample<T> {
1890 ///     fn deref_mut<'a>(&'a mut self) -> &'a mut T {
1891 ///         &mut self.value
1892 ///     }
1893 /// }
1894 ///
1895 /// fn main() {
1896 ///     let mut x = DerefMutExample { value: 'a' };
1897 ///     *x = 'b';
1898 ///     assert_eq!('b', *x);
1899 /// }
1900 /// ```
1901 #[lang = "deref_mut"]
1902 #[stable(feature = "rust1", since = "1.0.0")]
1903 pub trait DerefMut: Deref {
1904     /// The method called to mutably dereference a value
1905     #[stable(feature = "rust1", since = "1.0.0")]
1906     fn deref_mut(&mut self) -> &mut Self::Target;
1907 }
1908
1909 #[stable(feature = "rust1", since = "1.0.0")]
1910 impl<'a, T: ?Sized> DerefMut for &'a mut T {
1911     fn deref_mut(&mut self) -> &mut T { *self }
1912 }
1913
1914 /// A version of the call operator that takes an immutable receiver.
1915 #[lang = "fn"]
1916 #[stable(feature = "rust1", since = "1.0.0")]
1917 #[rustc_paren_sugar]
1918 #[fundamental] // so that regex can rely that `&str: !FnMut`
1919 pub trait Fn<Args> : FnMut<Args> {
1920     /// This is called when the call operator is used.
1921     #[unstable(feature = "fn_traits", issue = "29625")]
1922     extern "rust-call" fn call(&self, args: Args) -> Self::Output;
1923 }
1924
1925 /// A version of the call operator that takes a mutable receiver.
1926 #[lang = "fn_mut"]
1927 #[stable(feature = "rust1", since = "1.0.0")]
1928 #[rustc_paren_sugar]
1929 #[fundamental] // so that regex can rely that `&str: !FnMut`
1930 pub trait FnMut<Args> : FnOnce<Args> {
1931     /// This is called when the call operator is used.
1932     #[unstable(feature = "fn_traits", issue = "29625")]
1933     extern "rust-call" fn call_mut(&mut self, args: Args) -> Self::Output;
1934 }
1935
1936 /// A version of the call operator that takes a by-value receiver.
1937 #[lang = "fn_once"]
1938 #[stable(feature = "rust1", since = "1.0.0")]
1939 #[rustc_paren_sugar]
1940 #[fundamental] // so that regex can rely that `&str: !FnMut`
1941 pub trait FnOnce<Args> {
1942     /// The returned type after the call operator is used.
1943     #[stable(feature = "fn_once_output", since = "1.12.0")]
1944     type Output;
1945
1946     /// This is called when the call operator is used.
1947     #[unstable(feature = "fn_traits", issue = "29625")]
1948     extern "rust-call" fn call_once(self, args: Args) -> Self::Output;
1949 }
1950
1951 mod impls {
1952     use marker::Sized;
1953     use super::{Fn, FnMut, FnOnce};
1954
1955     #[stable(feature = "rust1", since = "1.0.0")]
1956     impl<'a,A,F:?Sized> Fn<A> for &'a F
1957         where F : Fn<A>
1958     {
1959         extern "rust-call" fn call(&self, args: A) -> F::Output {
1960             (**self).call(args)
1961         }
1962     }
1963
1964     #[stable(feature = "rust1", since = "1.0.0")]
1965     impl<'a,A,F:?Sized> FnMut<A> for &'a F
1966         where F : Fn<A>
1967     {
1968         extern "rust-call" fn call_mut(&mut self, args: A) -> F::Output {
1969             (**self).call(args)
1970         }
1971     }
1972
1973     #[stable(feature = "rust1", since = "1.0.0")]
1974     impl<'a,A,F:?Sized> FnOnce<A> for &'a F
1975         where F : Fn<A>
1976     {
1977         type Output = F::Output;
1978
1979         extern "rust-call" fn call_once(self, args: A) -> F::Output {
1980             (*self).call(args)
1981         }
1982     }
1983
1984     #[stable(feature = "rust1", since = "1.0.0")]
1985     impl<'a,A,F:?Sized> FnMut<A> for &'a mut F
1986         where F : FnMut<A>
1987     {
1988         extern "rust-call" fn call_mut(&mut self, args: A) -> F::Output {
1989             (*self).call_mut(args)
1990         }
1991     }
1992
1993     #[stable(feature = "rust1", since = "1.0.0")]
1994     impl<'a,A,F:?Sized> FnOnce<A> for &'a mut F
1995         where F : FnMut<A>
1996     {
1997         type Output = F::Output;
1998         extern "rust-call" fn call_once(mut self, args: A) -> F::Output {
1999             (*self).call_mut(args)
2000         }
2001     }
2002 }
2003
2004 /// Trait that indicates that this is a pointer or a wrapper for one,
2005 /// where unsizing can be performed on the pointee.
2006 #[unstable(feature = "coerce_unsized", issue = "27732")]
2007 #[lang="coerce_unsized"]
2008 pub trait CoerceUnsized<T> {
2009     // Empty.
2010 }
2011
2012 // &mut T -> &mut U
2013 #[unstable(feature = "coerce_unsized", issue = "27732")]
2014 impl<'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<&'a mut U> for &'a mut T {}
2015 // &mut T -> &U
2016 #[unstable(feature = "coerce_unsized", issue = "27732")]
2017 impl<'a, 'b: 'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b mut T {}
2018 // &mut T -> *mut U
2019 #[unstable(feature = "coerce_unsized", issue = "27732")]
2020 impl<'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for &'a mut T {}
2021 // &mut T -> *const U
2022 #[unstable(feature = "coerce_unsized", issue = "27732")]
2023 impl<'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*const U> for &'a mut T {}
2024
2025 // &T -> &U
2026 #[unstable(feature = "coerce_unsized", issue = "27732")]
2027 impl<'a, 'b: 'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
2028 // &T -> *const U
2029 #[unstable(feature = "coerce_unsized", issue = "27732")]
2030 impl<'a, T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*const U> for &'a T {}
2031
2032 // *mut T -> *mut U
2033 #[unstable(feature = "coerce_unsized", issue = "27732")]
2034 impl<T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
2035 // *mut T -> *const U
2036 #[unstable(feature = "coerce_unsized", issue = "27732")]
2037 impl<T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*const U> for *mut T {}
2038
2039 // *const T -> *const U
2040 #[unstable(feature = "coerce_unsized", issue = "27732")]
2041 impl<T: ?Sized+Unsize<U>, U: ?Sized> CoerceUnsized<*const U> for *const T {}
2042
2043 /// Both `in (PLACE) EXPR` and `box EXPR` desugar into expressions
2044 /// that allocate an intermediate "place" that holds uninitialized
2045 /// state.  The desugaring evaluates EXPR, and writes the result at
2046 /// the address returned by the `pointer` method of this trait.
2047 ///
2048 /// A `Place` can be thought of as a special representation for a
2049 /// hypothetical `&uninit` reference (which Rust cannot currently
2050 /// express directly). That is, it represents a pointer to
2051 /// uninitialized storage.
2052 ///
2053 /// The client is responsible for two steps: First, initializing the
2054 /// payload (it can access its address via `pointer`). Second,
2055 /// converting the agent to an instance of the owning pointer, via the
2056 /// appropriate `finalize` method (see the `InPlace`.
2057 ///
2058 /// If evaluating EXPR fails, then the destructor for the
2059 /// implementation of Place to clean up any intermediate state
2060 /// (e.g. deallocate box storage, pop a stack, etc).
2061 #[unstable(feature = "placement_new_protocol", issue = "27779")]
2062 pub trait Place<Data: ?Sized> {
2063     /// Returns the address where the input value will be written.
2064     /// Note that the data at this address is generally uninitialized,
2065     /// and thus one should use `ptr::write` for initializing it.
2066     fn pointer(&mut self) -> *mut Data;
2067 }
2068
2069 /// Interface to implementations of  `in (PLACE) EXPR`.
2070 ///
2071 /// `in (PLACE) EXPR` effectively desugars into:
2072 ///
2073 /// ```rust,ignore
2074 /// let p = PLACE;
2075 /// let mut place = Placer::make_place(p);
2076 /// let raw_place = Place::pointer(&mut place);
2077 /// let value = EXPR;
2078 /// unsafe {
2079 ///     std::ptr::write(raw_place, value);
2080 ///     InPlace::finalize(place)
2081 /// }
2082 /// ```
2083 ///
2084 /// The type of `in (PLACE) EXPR` is derived from the type of `PLACE`;
2085 /// if the type of `PLACE` is `P`, then the final type of the whole
2086 /// expression is `P::Place::Owner` (see the `InPlace` and `Boxed`
2087 /// traits).
2088 ///
2089 /// Values for types implementing this trait usually are transient
2090 /// intermediate values (e.g. the return value of `Vec::emplace_back`)
2091 /// or `Copy`, since the `make_place` method takes `self` by value.
2092 #[unstable(feature = "placement_new_protocol", issue = "27779")]
2093 pub trait Placer<Data: ?Sized> {
2094     /// `Place` is the intermedate agent guarding the
2095     /// uninitialized state for `Data`.
2096     type Place: InPlace<Data>;
2097
2098     /// Creates a fresh place from `self`.
2099     fn make_place(self) -> Self::Place;
2100 }
2101
2102 /// Specialization of `Place` trait supporting `in (PLACE) EXPR`.
2103 #[unstable(feature = "placement_new_protocol", issue = "27779")]
2104 pub trait InPlace<Data: ?Sized>: Place<Data> {
2105     /// `Owner` is the type of the end value of `in (PLACE) EXPR`
2106     ///
2107     /// Note that when `in (PLACE) EXPR` is solely used for
2108     /// side-effecting an existing data-structure,
2109     /// e.g. `Vec::emplace_back`, then `Owner` need not carry any
2110     /// information at all (e.g. it can be the unit type `()` in that
2111     /// case).
2112     type Owner;
2113
2114     /// Converts self into the final value, shifting
2115     /// deallocation/cleanup responsibilities (if any remain), over to
2116     /// the returned instance of `Owner` and forgetting self.
2117     unsafe fn finalize(self) -> Self::Owner;
2118 }
2119
2120 /// Core trait for the `box EXPR` form.
2121 ///
2122 /// `box EXPR` effectively desugars into:
2123 ///
2124 /// ```rust,ignore
2125 /// let mut place = BoxPlace::make_place();
2126 /// let raw_place = Place::pointer(&mut place);
2127 /// let value = EXPR;
2128 /// unsafe {
2129 ///     ::std::ptr::write(raw_place, value);
2130 ///     Boxed::finalize(place)
2131 /// }
2132 /// ```
2133 ///
2134 /// The type of `box EXPR` is supplied from its surrounding
2135 /// context; in the above expansion, the result type `T` is used
2136 /// to determine which implementation of `Boxed` to use, and that
2137 /// `<T as Boxed>` in turn dictates determines which
2138 /// implementation of `BoxPlace` to use, namely:
2139 /// `<<T as Boxed>::Place as BoxPlace>`.
2140 #[unstable(feature = "placement_new_protocol", issue = "27779")]
2141 pub trait Boxed {
2142     /// The kind of data that is stored in this kind of box.
2143     type Data;  /* (`Data` unused b/c cannot yet express below bound.) */
2144     /// The place that will negotiate the storage of the data.
2145     type Place: BoxPlace<Self::Data>;
2146
2147     /// Converts filled place into final owning value, shifting
2148     /// deallocation/cleanup responsibilities (if any remain), over to
2149     /// returned instance of `Self` and forgetting `filled`.
2150     unsafe fn finalize(filled: Self::Place) -> Self;
2151 }
2152
2153 /// Specialization of `Place` trait supporting `box EXPR`.
2154 #[unstable(feature = "placement_new_protocol", issue = "27779")]
2155 pub trait BoxPlace<Data: ?Sized> : Place<Data> {
2156     /// Creates a globally fresh place.
2157     fn make_place() -> Self;
2158 }