2014-05-12 04:04:07 -05:00
|
|
|
// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
|
2012-12-03 18:48:01 -06:00
|
|
|
// file at the top-level directory of this distribution and at
|
|
|
|
// http://rust-lang.org/COPYRIGHT.
|
|
|
|
//
|
|
|
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
|
|
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
|
|
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
|
|
|
// option. This file may not be copied, modified, or distributed
|
|
|
|
// except according to those terms.
|
|
|
|
|
2014-05-29 19:45:07 -05:00
|
|
|
//! Defines the `PartialOrd` and `PartialEq` comparison traits.
|
2014-04-06 09:20:53 -05:00
|
|
|
//!
|
2014-05-29 19:45:07 -05:00
|
|
|
//! This module defines both `PartialOrd` and `PartialEq` traits which are used by the
|
2014-04-06 09:20:53 -05:00
|
|
|
//! compiler to implement comparison operators. Rust programs may implement
|
2014-05-29 19:45:07 -05:00
|
|
|
//!`PartialOrd` to overload the `<`, `<=`, `>`, and `>=` operators, and may implement
|
|
|
|
//! `PartialEq` to overload the `==` and `!=` operators.
|
2014-04-06 09:20:53 -05:00
|
|
|
//!
|
2014-05-29 19:45:07 -05:00
|
|
|
//! For example, to define a type with a customized definition for the PartialEq
|
2014-04-06 09:20:53 -05:00
|
|
|
//! operators, you could do the following:
|
|
|
|
//!
|
|
|
|
//! ```rust
|
2014-11-12 07:02:42 -06:00
|
|
|
//! use core::num::SignedInt;
|
|
|
|
//!
|
2014-04-06 09:20:53 -05:00
|
|
|
//! // Our type.
|
|
|
|
//! struct SketchyNum {
|
|
|
|
//! num : int
|
|
|
|
//! }
|
|
|
|
//!
|
2014-05-29 19:45:07 -05:00
|
|
|
//! // Our implementation of `PartialEq` to support `==` and `!=`.
|
|
|
|
//! impl PartialEq for SketchyNum {
|
2014-04-20 23:49:39 -05:00
|
|
|
//! // Our custom eq allows numbers which are near each other to be equal! :D
|
2014-04-06 09:20:53 -05:00
|
|
|
//! fn eq(&self, other: &SketchyNum) -> bool {
|
|
|
|
//! (self.num - other.num).abs() < 5
|
|
|
|
//! }
|
|
|
|
//! }
|
|
|
|
//!
|
|
|
|
//! // Now these binary operators will work when applied!
|
|
|
|
//! assert!(SketchyNum {num: 37} == SketchyNum {num: 34});
|
|
|
|
//! assert!(SketchyNum {num: 25} != SketchyNum {num: 57});
|
|
|
|
//! ```
|
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#![stable(feature = "rust1", since = "1.0.0")]
|
2014-07-18 17:59:54 -05:00
|
|
|
|
2014-12-22 13:09:55 -06:00
|
|
|
use self::Ordering::*;
|
2014-11-06 02:05:53 -06:00
|
|
|
|
2015-01-06 16:33:42 -06:00
|
|
|
use marker::Sized;
|
2015-01-03 21:42:21 -06:00
|
|
|
use option::Option::{self, Some, None};
|
2014-06-18 01:25:51 -05:00
|
|
|
|
2014-12-30 16:44:26 -06:00
|
|
|
/// Trait for equality comparisons which are [partial equivalence relations](
|
|
|
|
/// http://en.wikipedia.org/wiki/Partial_equivalence_relation).
|
2014-04-06 09:20:53 -05:00
|
|
|
///
|
2014-12-30 16:44:26 -06:00
|
|
|
/// This trait allows for partial equality, for types that do not have a full
|
2014-06-07 15:38:24 -05:00
|
|
|
/// equivalence relation. For example, in floating point numbers `NaN != NaN`,
|
|
|
|
/// so floating point types implement `PartialEq` but not `Eq`.
|
2014-04-06 09:20:53 -05:00
|
|
|
///
|
2014-12-30 16:44:26 -06:00
|
|
|
/// Formally, the equality must be (for all `a`, `b` and `c`):
|
|
|
|
///
|
|
|
|
/// - symmetric: `a == b` implies `b == a`; and
|
|
|
|
/// - transitive: `a == b` and `b == c` implies `a == c`.
|
|
|
|
///
|
|
|
|
/// Note that these requirements mean that the trait itself must be
|
|
|
|
/// implemented symmetrically and transitively: if `T: PartialEq<U>`
|
|
|
|
/// and `U: PartialEq<V>` then `U: PartialEq<T>` and `T:
|
|
|
|
/// PartialEq<V>`.
|
|
|
|
///
|
2014-06-07 19:50:45 -05:00
|
|
|
/// PartialEq only requires the `eq` method to be implemented; `ne` is defined
|
|
|
|
/// in terms of it by default. Any manual implementation of `ne` *must* respect
|
|
|
|
/// the rule that `eq` is a strict inverse of `ne`; that is, `!(a == b)` if and
|
|
|
|
/// only if `a != b`.
|
2014-10-29 20:11:16 -05:00
|
|
|
#[lang="eq"]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
Implement new orphan rule that requires that impls of remote traits meet the following two criteria:
- the self type includes some local type; and,
- type parameters in the self type must be constrained by a local type.
A type parameter is called *constrained* if it appears in some type-parameter of a local type.
Here are some examples that are accepted. In all of these examples, I
assume that `Foo` is a trait defined in another crate. If `Foo` were
defined in the local crate, then all the examples would be legal.
- `impl Foo for LocalType`
- `impl<T> Foo<T> for LocalType` -- T does not appear in Self, so it is OK
- `impl<T> Foo<T> for LocalType<T>` -- T here is constrained by LocalType
- `impl<T> Foo<T> for (LocalType<T>, T)` -- T here is constrained by LocalType
Here are some illegal examples (again, these examples assume that
`Foo` is not local to the current crate):
- `impl Foo for int` -- the Self type is not local
- `impl<T> Foo for T` -- T appears in Self unconstrained by a local type
- `impl<T> Foo for (LocalType, T)` -- T appears in Self unconstrained by a local type
This is a [breaking-change]. For the time being, you can opt out of
the new rules by placing `#[old_orphan_check]` on the trait (and
enabling the feature gate where the trait is defined). Longer term,
you should restructure your traits to avoid the problem. Usually this
means changing the order of parameters so that the "central" type
parameter is in the `Self` position.
As an example of that refactoring, consider the `BorrowFrom` trait:
```rust
pub trait BorrowFrom<Sized? Owned> for Sized? {
fn borrow_from(owned: &Owned) -> &Self;
}
```
As defined, this trait is commonly implemented for custom pointer
types, such as `Arc`. Those impls follow the pattern:
```rust
impl<T> BorrowFrom<Arc<T>> for T {...}
```
Unfortunately, this impl is illegal because the self type `T` is not
local to the current crate. Therefore, we are going to change the order of the parameters,
so that `BorrowFrom` becomes `Borrow`:
```rust
pub trait Borrow<Sized? Borrowed> for Sized? {
fn borrow_from(owned: &Self) -> &Borrowed;
}
```
Now the `Arc` impl is written:
```rust
impl<T> Borrow<T> for Arc<T> { ... }
```
This impl is legal because the self type (`Arc<T>`) is local.
2015-01-04 19:35:06 -06:00
|
|
|
#[old_orphan_check]
|
2015-01-05 20:55:41 -06:00
|
|
|
pub trait PartialEq<Rhs: ?Sized = Self> {
|
2014-10-29 20:11:16 -05:00
|
|
|
/// This method tests for `self` and `other` values to be equal, and is used by `==`.
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn eq(&self, other: &Rhs) -> bool;
|
2014-10-29 20:11:16 -05:00
|
|
|
|
|
|
|
/// This method tests for `!=`.
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn ne(&self, other: &Rhs) -> bool { !self.eq(other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
|
|
|
|
2014-04-06 09:20:53 -05:00
|
|
|
/// Trait for equality comparisons which are [equivalence relations](
|
|
|
|
/// https://en.wikipedia.org/wiki/Equivalence_relation).
|
|
|
|
///
|
|
|
|
/// This means, that in addition to `a == b` and `a != b` being strict
|
|
|
|
/// inverses, the equality must be (for all `a`, `b` and `c`):
|
|
|
|
///
|
|
|
|
/// - reflexive: `a == a`;
|
|
|
|
/// - symmetric: `a == b` implies `b == a`; and
|
|
|
|
/// - transitive: `a == b` and `b == c` implies `a == c`.
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-04 20:39:02 -06:00
|
|
|
pub trait Eq: PartialEq<Self> {
|
2014-10-29 20:11:16 -05:00
|
|
|
// FIXME #13101: this method is used solely by #[deriving] to
|
|
|
|
// assert that every component of a type implements #[deriving]
|
|
|
|
// itself, the current deriving infrastructure means doing this
|
|
|
|
// assertion without using a method on this trait is nearly
|
|
|
|
// impossible.
|
|
|
|
//
|
|
|
|
// This should never be implemented by hand.
|
|
|
|
#[doc(hidden)]
|
|
|
|
#[inline(always)]
|
|
|
|
fn assert_receiver_is_total_eq(&self) {}
|
|
|
|
}
|
|
|
|
|
2014-03-16 16:26:54 -05:00
|
|
|
/// An ordering is, e.g, a result of a comparison between two values.
|
2015-01-28 07:34:18 -06:00
|
|
|
#[derive(Clone, Copy, PartialEq, Debug)]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-03-16 16:26:54 -05:00
|
|
|
pub enum Ordering {
|
2014-12-30 16:44:26 -06:00
|
|
|
/// An ordering where a compared value is less [than another].
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-22 08:08:56 -06:00
|
|
|
Less = -1,
|
2014-12-30 16:44:26 -06:00
|
|
|
/// An ordering where a compared value is equal [to another].
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-22 08:08:56 -06:00
|
|
|
Equal = 0,
|
2014-12-30 16:44:26 -06:00
|
|
|
/// An ordering where a compared value is greater [than another].
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-22 08:08:56 -06:00
|
|
|
Greater = 1,
|
2014-03-16 16:26:54 -05:00
|
|
|
}
|
2013-03-01 21:07:12 -06:00
|
|
|
|
2014-07-31 21:53:00 -05:00
|
|
|
impl Ordering {
|
|
|
|
/// Reverse the `Ordering`, so that `Less` becomes `Greater` and
|
|
|
|
/// vice versa.
|
|
|
|
///
|
|
|
|
/// # Example
|
|
|
|
///
|
|
|
|
/// ```rust
|
2014-12-22 11:04:23 -06:00
|
|
|
/// use std::cmp::Ordering::{Less, Equal, Greater};
|
|
|
|
///
|
2014-07-31 21:53:00 -05:00
|
|
|
/// assert_eq!(Less.reverse(), Greater);
|
|
|
|
/// assert_eq!(Equal.reverse(), Equal);
|
|
|
|
/// assert_eq!(Greater.reverse(), Less);
|
|
|
|
///
|
2015-01-22 08:08:56 -06:00
|
|
|
/// let mut data: &mut [_] = &mut [2, 10, 5, 8];
|
2014-07-31 21:53:00 -05:00
|
|
|
///
|
|
|
|
/// // sort the array from largest to smallest.
|
|
|
|
/// data.sort_by(|a, b| a.cmp(b).reverse());
|
|
|
|
///
|
2015-01-22 08:08:56 -06:00
|
|
|
/// let b: &mut [_] = &mut [10, 8, 5, 2];
|
2014-08-06 04:59:40 -05:00
|
|
|
/// assert!(data == b);
|
2014-07-31 21:53:00 -05:00
|
|
|
/// ```
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-07-31 21:53:00 -05:00
|
|
|
pub fn reverse(self) -> Ordering {
|
|
|
|
unsafe {
|
|
|
|
// this compiles really nicely (to a single instruction);
|
|
|
|
// an explicit match has a pile of branches and
|
|
|
|
// comparisons.
|
|
|
|
//
|
|
|
|
// NB. it is safe because of the explicit discriminants
|
|
|
|
// given above.
|
|
|
|
::mem::transmute::<_, Ordering>(-(self as i8))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-04-06 09:20:53 -05:00
|
|
|
/// Trait for types that form a [total order](
|
|
|
|
/// https://en.wikipedia.org/wiki/Total_order).
|
|
|
|
///
|
|
|
|
/// An order is a total order if it is (for all `a`, `b` and `c`):
|
|
|
|
///
|
|
|
|
/// - total and antisymmetric: exactly one of `a < b`, `a == b` or `a > b` is
|
|
|
|
/// true; and
|
|
|
|
/// - transitive, `a < b` and `b < c` implies `a < c`. The same must hold for
|
|
|
|
/// both `==` and `>`.
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-04 20:39:02 -06:00
|
|
|
pub trait Ord: Eq + PartialOrd<Self> {
|
2014-10-29 20:11:16 -05:00
|
|
|
/// This method returns an ordering between `self` and `other` values.
|
|
|
|
///
|
|
|
|
/// By convention, `self.cmp(&other)` returns the ordering matching
|
|
|
|
/// the expression `self <operator> other` if true. For example:
|
|
|
|
///
|
|
|
|
/// ```
|
2014-12-22 11:04:23 -06:00
|
|
|
/// use std::cmp::Ordering::{Less, Equal, Greater};
|
|
|
|
///
|
2015-01-22 08:08:56 -06:00
|
|
|
/// assert_eq!( 5.cmp(&10), Less); // because 5 < 10
|
|
|
|
/// assert_eq!(10.cmp(&5), Greater); // because 10 > 5
|
|
|
|
/// assert_eq!( 5.cmp(&5), Equal); // because 5 == 5
|
2014-10-29 20:11:16 -05:00
|
|
|
/// ```
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn cmp(&self, other: &Self) -> Ordering;
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Eq for Ordering {}
|
2014-04-30 23:55:14 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Ord for Ordering {
|
2013-06-18 16:45:18 -05:00
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2013-04-06 23:49:10 -05:00
|
|
|
fn cmp(&self, other: &Ordering) -> Ordering {
|
|
|
|
(*self as int).cmp(&(*other as int))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialOrd for Ordering {
|
2013-06-18 16:45:18 -05:00
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-06-18 01:25:51 -05:00
|
|
|
fn partial_cmp(&self, other: &Ordering) -> Option<Ordering> {
|
|
|
|
(*self as int).partial_cmp(&(*other as int))
|
|
|
|
}
|
2013-04-06 23:49:10 -05:00
|
|
|
}
|
|
|
|
|
2014-04-06 09:20:53 -05:00
|
|
|
/// Trait for values that can be compared for a sort-order.
|
|
|
|
///
|
2014-12-30 16:44:26 -06:00
|
|
|
/// The comparison must satisfy, for all `a`, `b` and `c`:
|
|
|
|
///
|
|
|
|
/// - antisymmetry: if `a < b` then `!(a > b)` and vice versa; and
|
|
|
|
/// - transitivity: `a < b` and `b < c` implies `a < c`. The same must hold for
|
|
|
|
/// both `==` and `>`.
|
|
|
|
///
|
|
|
|
/// Note that these requirements mean that the trait itself must be
|
|
|
|
/// implemented symmetrically and transitively: if `T: PartialOrd<U>`
|
|
|
|
/// and `U: PartialOrd<V>` then `U: PartialOrd<T>` and `T:
|
|
|
|
/// PartialOrd<V>`.
|
|
|
|
///
|
2014-06-18 01:25:51 -05:00
|
|
|
/// PartialOrd only requires implementation of the `partial_cmp` method,
|
2014-04-06 09:20:53 -05:00
|
|
|
/// with the others generated from default implementations.
|
|
|
|
///
|
2014-06-07 15:38:24 -05:00
|
|
|
/// However it remains possible to implement the others separately for types
|
|
|
|
/// which do not have a total order. For example, for floating point numbers,
|
|
|
|
/// `NaN < 0 == false` and `NaN >= 0 == false` (cf. IEEE 754-2008 section
|
|
|
|
/// 5.11).
|
2014-10-29 20:11:16 -05:00
|
|
|
#[lang="ord"]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 20:55:41 -06:00
|
|
|
pub trait PartialOrd<Rhs: ?Sized = Self>: PartialEq<Rhs> {
|
2014-10-29 20:11:16 -05:00
|
|
|
/// This method returns an ordering between `self` and `other` values
|
|
|
|
/// if one exists.
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn partial_cmp(&self, other: &Rhs) -> Option<Ordering>;
|
2014-10-29 20:11:16 -05:00
|
|
|
|
|
|
|
/// This method tests less than (for `self` and `other`) and is used by the `<` operator.
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn lt(&self, other: &Rhs) -> bool {
|
2014-10-29 20:11:16 -05:00
|
|
|
match self.partial_cmp(other) {
|
|
|
|
Some(Less) => true,
|
|
|
|
_ => false,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// This method tests less than or equal to (`<=`).
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn le(&self, other: &Rhs) -> bool {
|
2014-10-29 20:11:16 -05:00
|
|
|
match self.partial_cmp(other) {
|
|
|
|
Some(Less) | Some(Equal) => true,
|
|
|
|
_ => false,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// This method tests greater than (`>`).
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn gt(&self, other: &Rhs) -> bool {
|
2014-10-29 20:11:16 -05:00
|
|
|
match self.partial_cmp(other) {
|
|
|
|
Some(Greater) => true,
|
|
|
|
_ => false,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// This method tests greater than or equal to (`>=`).
|
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-11-20 17:17:37 -06:00
|
|
|
fn ge(&self, other: &Rhs) -> bool {
|
2014-10-29 20:11:16 -05:00
|
|
|
match self.partial_cmp(other) {
|
|
|
|
Some(Greater) | Some(Equal) => true,
|
|
|
|
_ => false,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-03-16 16:26:54 -05:00
|
|
|
/// Compare and return the minimum of two values.
|
2013-06-18 16:45:18 -05:00
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
pub fn min<T: Ord>(v1: T, v2: T) -> T {
|
2013-01-15 19:30:01 -06:00
|
|
|
if v1 < v2 { v1 } else { v2 }
|
|
|
|
}
|
|
|
|
|
2014-03-16 16:26:54 -05:00
|
|
|
/// Compare and return the maximum of two values.
|
2013-06-18 16:45:18 -05:00
|
|
|
#[inline]
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
pub fn max<T: Ord>(v1: T, v2: T) -> T {
|
2013-01-15 19:30:01 -06:00
|
|
|
if v1 > v2 { v1 } else { v2 }
|
|
|
|
}
|
2013-03-01 21:07:12 -06:00
|
|
|
|
2014-09-23 13:01:59 -05:00
|
|
|
/// Compare and return the minimum of two values if there is one.
|
|
|
|
///
|
|
|
|
/// Returns the first argument if the comparison determines them to be equal.
|
|
|
|
#[inline]
|
2015-01-22 20:22:03 -06:00
|
|
|
#[unstable(feature = "core")]
|
2014-09-23 13:01:59 -05:00
|
|
|
pub fn partial_min<T: PartialOrd>(v1: T, v2: T) -> Option<T> {
|
|
|
|
match v1.partial_cmp(&v2) {
|
|
|
|
Some(Less) | Some(Equal) => Some(v1),
|
|
|
|
Some(Greater) => Some(v2),
|
|
|
|
None => None
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/// Compare and return the maximum of two values if there is one.
|
|
|
|
///
|
|
|
|
/// Returns the first argument if the comparison determines them to be equal.
|
|
|
|
#[inline]
|
2015-01-22 20:22:03 -06:00
|
|
|
#[unstable(feature = "core")]
|
2014-09-23 13:01:59 -05:00
|
|
|
pub fn partial_max<T: PartialOrd>(v1: T, v2: T) -> Option<T> {
|
|
|
|
match v1.partial_cmp(&v2) {
|
|
|
|
Some(Less) => Some(v2),
|
|
|
|
Some(Equal) | Some(Greater) => Some(v1),
|
|
|
|
None => None
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-05-31 12:43:52 -05:00
|
|
|
// Implementation of PartialEq, Eq, PartialOrd and Ord for primitive types
|
2014-05-01 00:00:31 -05:00
|
|
|
mod impls {
|
2014-11-28 10:57:41 -06:00
|
|
|
use cmp::{PartialOrd, Ord, PartialEq, Eq, Ordering};
|
|
|
|
use cmp::Ordering::{Less, Greater, Equal};
|
2015-01-06 16:33:42 -06:00
|
|
|
use marker::Sized;
|
2014-11-28 10:57:41 -06:00
|
|
|
use option::Option;
|
|
|
|
use option::Option::{Some, None};
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
macro_rules! partial_eq_impl {
|
2014-05-26 12:33:04 -05:00
|
|
|
($($t:ty)*) => ($(
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialEq for $t {
|
2014-05-26 12:33:04 -05:00
|
|
|
#[inline]
|
|
|
|
fn eq(&self, other: &$t) -> bool { (*self) == (*other) }
|
|
|
|
#[inline]
|
|
|
|
fn ne(&self, other: &$t) -> bool { (*self) != (*other) }
|
|
|
|
}
|
|
|
|
)*)
|
2014-11-14 11:18:10 -06:00
|
|
|
}
|
2014-05-12 23:02:27 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialEq for () {
|
2014-05-12 23:02:27 -05:00
|
|
|
#[inline]
|
|
|
|
fn eq(&self, _other: &()) -> bool { true }
|
|
|
|
#[inline]
|
|
|
|
fn ne(&self, _other: &()) -> bool { false }
|
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
partial_eq_impl! {
|
|
|
|
bool char uint u8 u16 u32 u64 int i8 i16 i32 i64 f32 f64
|
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
macro_rules! eq_impl {
|
2014-05-26 12:33:04 -05:00
|
|
|
($($t:ty)*) => ($(
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Eq for $t {}
|
2014-05-26 12:33:04 -05:00
|
|
|
)*)
|
2014-11-14 11:18:10 -06:00
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
eq_impl! { () bool char uint u8 u16 u32 u64 int i8 i16 i32 i64 }
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
macro_rules! partial_ord_impl {
|
2014-05-26 12:33:04 -05:00
|
|
|
($($t:ty)*) => ($(
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialOrd for $t {
|
2014-06-18 01:25:51 -05:00
|
|
|
#[inline]
|
|
|
|
fn partial_cmp(&self, other: &$t) -> Option<Ordering> {
|
|
|
|
match (self <= other, self >= other) {
|
|
|
|
(false, false) => None,
|
|
|
|
(false, true) => Some(Greater),
|
|
|
|
(true, false) => Some(Less),
|
|
|
|
(true, true) => Some(Equal),
|
|
|
|
}
|
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
#[inline]
|
|
|
|
fn lt(&self, other: &$t) -> bool { (*self) < (*other) }
|
|
|
|
#[inline]
|
|
|
|
fn le(&self, other: &$t) -> bool { (*self) <= (*other) }
|
|
|
|
#[inline]
|
|
|
|
fn ge(&self, other: &$t) -> bool { (*self) >= (*other) }
|
|
|
|
#[inline]
|
|
|
|
fn gt(&self, other: &$t) -> bool { (*self) > (*other) }
|
|
|
|
}
|
|
|
|
)*)
|
2014-11-14 11:18:10 -06:00
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialOrd for () {
|
2014-05-12 23:02:27 -05:00
|
|
|
#[inline]
|
2014-06-18 01:25:51 -05:00
|
|
|
fn partial_cmp(&self, _: &()) -> Option<Ordering> {
|
|
|
|
Some(Equal)
|
|
|
|
}
|
2014-05-12 23:02:27 -05:00
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-29 19:45:07 -05:00
|
|
|
impl PartialOrd for bool {
|
2014-05-26 12:33:04 -05:00
|
|
|
#[inline]
|
2014-06-18 01:25:51 -05:00
|
|
|
fn partial_cmp(&self, other: &bool) -> Option<Ordering> {
|
|
|
|
(*self as u8).partial_cmp(&(*other as u8))
|
2014-05-26 12:33:04 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
partial_ord_impl! { char uint u8 u16 u32 u64 int i8 i16 i32 i64 f32 f64 }
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
macro_rules! ord_impl {
|
2014-05-26 12:33:04 -05:00
|
|
|
($($t:ty)*) => ($(
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Ord for $t {
|
2014-05-26 12:33:04 -05:00
|
|
|
#[inline]
|
|
|
|
fn cmp(&self, other: &$t) -> Ordering {
|
|
|
|
if *self < *other { Less }
|
|
|
|
else if *self > *other { Greater }
|
|
|
|
else { Equal }
|
|
|
|
}
|
|
|
|
}
|
|
|
|
)*)
|
2014-11-14 11:18:10 -06:00
|
|
|
}
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Ord for () {
|
2014-05-12 23:02:27 -05:00
|
|
|
#[inline]
|
|
|
|
fn cmp(&self, _other: &()) -> Ordering { Equal }
|
|
|
|
}
|
2014-05-01 00:00:31 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2014-05-31 12:43:52 -05:00
|
|
|
impl Ord for bool {
|
2014-05-26 12:33:04 -05:00
|
|
|
#[inline]
|
|
|
|
fn cmp(&self, other: &bool) -> Ordering {
|
|
|
|
(*self as u8).cmp(&(*other as u8))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-11-14 11:18:10 -06:00
|
|
|
ord_impl! { char uint u8 u16 u32 u64 int i8 i16 i32 i64 }
|
2014-05-26 12:33:04 -05:00
|
|
|
|
2014-05-01 00:00:31 -05:00
|
|
|
// & pointers
|
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialEq<&'b B> for &'a A where A: PartialEq<B> {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-11-20 23:14:05 -06:00
|
|
|
fn eq(&self, other: & &'b B) -> bool { PartialEq::eq(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-11-20 23:14:05 -06:00
|
|
|
fn ne(&self, other: & &'b B) -> bool { PartialEq::ne(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialOrd<&'b B> for &'a A where A: PartialOrd<B> {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn partial_cmp(&self, other: &&'b B) -> Option<Ordering> {
|
2014-10-29 20:11:16 -05:00
|
|
|
PartialOrd::partial_cmp(*self, *other)
|
|
|
|
}
|
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn lt(&self, other: & &'b B) -> bool { PartialOrd::lt(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn le(&self, other: & &'b B) -> bool { PartialOrd::le(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn ge(&self, other: & &'b B) -> bool { PartialOrd::ge(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn gt(&self, other: & &'b B) -> bool { PartialOrd::gt(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, A: ?Sized> Ord for &'a A where A: Ord {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn cmp(&self, other: & &'a A) -> Ordering { Ord::cmp(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, A: ?Sized> Eq for &'a A where A: Eq {}
|
2014-10-29 20:11:16 -05:00
|
|
|
|
2014-05-12 04:04:07 -05:00
|
|
|
// &mut pointers
|
2014-10-29 20:11:16 -05:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialEq<&'b mut B> for &'a mut A where A: PartialEq<B> {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-11-20 23:14:05 -06:00
|
|
|
fn eq(&self, other: &&'b mut B) -> bool { PartialEq::eq(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-11-20 23:14:05 -06:00
|
|
|
fn ne(&self, other: &&'b mut B) -> bool { PartialEq::ne(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialOrd<&'b mut B> for &'a mut A where A: PartialOrd<B> {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn partial_cmp(&self, other: &&'b mut B) -> Option<Ordering> {
|
2014-10-29 20:11:16 -05:00
|
|
|
PartialOrd::partial_cmp(*self, *other)
|
|
|
|
}
|
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn lt(&self, other: &&'b mut B) -> bool { PartialOrd::lt(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn le(&self, other: &&'b mut B) -> bool { PartialOrd::le(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn ge(&self, other: &&'b mut B) -> bool { PartialOrd::ge(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn gt(&self, other: &&'b mut B) -> bool { PartialOrd::gt(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, A: ?Sized> Ord for &'a mut A where A: Ord {
|
2014-10-29 20:11:16 -05:00
|
|
|
#[inline]
|
2014-12-30 16:44:26 -06:00
|
|
|
fn cmp(&self, other: &&'a mut A) -> Ordering { Ord::cmp(*self, *other) }
|
2014-10-29 20:11:16 -05:00
|
|
|
}
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, A: ?Sized> Eq for &'a mut A where A: Eq {}
|
2014-11-20 23:14:05 -06:00
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialEq<&'b mut B> for &'a A where A: PartialEq<B> {
|
2014-11-20 23:14:05 -06:00
|
|
|
#[inline]
|
|
|
|
fn eq(&self, other: &&'b mut B) -> bool { PartialEq::eq(*self, *other) }
|
|
|
|
#[inline]
|
|
|
|
fn ne(&self, other: &&'b mut B) -> bool { PartialEq::ne(*self, *other) }
|
|
|
|
}
|
|
|
|
|
2015-01-23 23:48:20 -06:00
|
|
|
#[stable(feature = "rust1", since = "1.0.0")]
|
2015-01-05 15:16:49 -06:00
|
|
|
impl<'a, 'b, A: ?Sized, B: ?Sized> PartialEq<&'b B> for &'a mut A where A: PartialEq<B> {
|
2014-11-20 23:14:05 -06:00
|
|
|
#[inline]
|
|
|
|
fn eq(&self, other: &&'b B) -> bool { PartialEq::eq(*self, *other) }
|
|
|
|
#[inline]
|
|
|
|
fn ne(&self, other: &&'b B) -> bool { PartialEq::ne(*self, *other) }
|
|
|
|
}
|
2014-05-01 00:00:31 -05:00
|
|
|
}
|