|
21 | 21 | //! custom operators are required, you should look toward macros or compiler
|
22 | 22 | //! plugins to extend Rust's syntax.
|
23 | 23 | //!
|
| 24 | +//! Note that the `&&` and `||` operators short-circuit, i.e. they only |
| 25 | +//! evaluate their second operand if it contributes to the result. Since this |
| 26 | +//! behavior is not enforceable by traits, `&&` and `||` are not supported as |
| 27 | +//! overloadable operators. |
| 28 | +//! |
24 | 29 | //! Many of the operators take their operands by value. In non-generic
|
25 | 30 | //! contexts involving built-in types, this is usually not a problem.
|
26 | 31 | //! However, using these operators in generic code, requires some
|
@@ -793,41 +798,56 @@ not_impl! { bool usize u8 u16 u32 u64 isize i8 i16 i32 i64 }
|
793 | 798 | ///
|
794 | 799 | /// # Examples
|
795 | 800 | ///
|
796 |
| -/// In this example, the `BitAnd` trait is implemented for a `BooleanVector` |
797 |
| -/// struct. |
| 801 | +/// In this example, the `&` operator is lifted to a trivial `Scalar` type. |
798 | 802 | ///
|
799 | 803 | /// ```
|
800 | 804 | /// use std::ops::BitAnd;
|
801 | 805 | ///
|
802 |
| -/// #[derive(Debug)] |
803 |
| -/// struct BooleanVector { |
804 |
| -/// value: Vec<bool>, |
805 |
| -/// }; |
| 806 | +/// #[derive(Debug, PartialEq)] |
| 807 | +/// struct Scalar(bool); |
806 | 808 | ///
|
807 |
| -/// impl BitAnd for BooleanVector { |
| 809 | +/// impl BitAnd for Scalar { |
808 | 810 | /// type Output = Self;
|
809 | 811 | ///
|
| 812 | +/// // rhs is the "right-hand side" of the expression `a & b` |
810 | 813 | /// fn bitand(self, rhs: Self) -> Self {
|
811 |
| -/// BooleanVector { |
812 |
| -/// value: self.value |
813 |
| -/// .iter() |
814 |
| -/// .zip(rhs.value.iter()) |
815 |
| -/// .map(|(x, y)| *x && *y) |
816 |
| -/// .collect(), |
817 |
| -/// } |
| 814 | +/// Scalar(self.0 & rhs.0) |
818 | 815 | /// }
|
819 | 816 | /// }
|
820 | 817 | ///
|
821 |
| -/// impl PartialEq for BooleanVector { |
822 |
| -/// fn eq(&self, other: &Self) -> bool { |
823 |
| -/// self.value == other.value |
| 818 | +/// fn main() { |
| 819 | +/// assert_eq!(Scalar(true) & Scalar(true), Scalar(true)); |
| 820 | +/// assert_eq!(Scalar(true) & Scalar(false), Scalar(false)); |
| 821 | +/// assert_eq!(Scalar(false) & Scalar(true), Scalar(false)); |
| 822 | +/// assert_eq!(Scalar(false) & Scalar(false), Scalar(false)); |
| 823 | +/// } |
| 824 | +/// ``` |
| 825 | +/// |
| 826 | +/// In this example, the `BitAnd` trait is implemented for a `BooleanVector` |
| 827 | +/// struct. |
| 828 | +/// |
| 829 | +/// ``` |
| 830 | +/// use std::ops::BitAnd; |
| 831 | +/// |
| 832 | +/// #[derive(Debug, PartialEq)] |
| 833 | +/// struct BooleanVector(Vec<bool>); |
| 834 | +/// |
| 835 | +/// impl BitAnd for BooleanVector { |
| 836 | +/// type Output = Self; |
| 837 | +/// |
| 838 | +/// fn bitand(self, BooleanVector(rhs): Self) -> Self { |
| 839 | +/// let BooleanVector(lhs) = self; |
| 840 | +/// assert_eq!(lhs.len(), rhs.len()); |
| 841 | +/// BooleanVector(lhs.iter().zip(rhs.iter()).map(|(x, y)| *x && *y).collect()) |
824 | 842 | /// }
|
825 | 843 | /// }
|
826 | 844 | ///
|
827 |
| -/// let bv1 = BooleanVector { value: vec![true, true, false, false] }; |
828 |
| -/// let bv2 = BooleanVector { value: vec![true, false, true, false] }; |
829 |
| -/// let expected = BooleanVector { value: vec![true, false, false, false] }; |
830 |
| -/// assert_eq!(bv1 & bv2, expected); |
| 845 | +/// fn main() { |
| 846 | +/// let bv1 = BooleanVector(vec![true, true, false, false]); |
| 847 | +/// let bv2 = BooleanVector(vec![true, false, true, false]); |
| 848 | +/// let expected = BooleanVector(vec![true, false, false, false]); |
| 849 | +/// assert_eq!(bv1 & bv2, expected); |
| 850 | +/// } |
831 | 851 | /// ```
|
832 | 852 | #[lang = "bitand"]
|
833 | 853 | #[stable(feature = "rust1", since = "1.0.0")]
|
|
0 commit comments