运算符

Rust中的运算符几乎都与一个trait相对应。

一元运算符

-:取负,专门用于数值类型。实现了 std::ops::Neg。

*:解引用。实现了 std::ops::Deref 或 std::ops::DerefMut。

!:取反。例如 !false 相当于 true。有意思的是,如果这个操作符对数字类型使用,会将其每一位都置反!也就是说,对一个 1u8 进行 ! 操作,将得到一个 254u8。实现了 std::ops::Not。

二元运算符

算数操作符

  • :加法。实现了 std::ops::Add。

-:减法。实现了 std::ops::Sub。

* :乘法。实现了 std::ops::Mul。

/ :除法。实现了 std::ops::Div。

% :取余。实现了 std::ops::Rem。

位运算符

& :与操作。实现了 std::ops::BitAnd。

| :或操作。实现了 std::ops::BitOr。

^ :异或。实现了 std::ops::BitXor。

<< :左移运算符。实现了 std::ops::Shl。

>> :右移运算符。实现了 std::ops::Shr。

比较运算符

比较运算符实际上也是某些 trait 的语法糖,不过比较运算符所实现的 trait 只有2个:

  • std::cmp::PartialEq 代表== 与 !=
  • std::cmp::PartialOrd 代表 < > >= <=

PartialEq与PartialOrd代表了偏序关系。

标准库中,std::cmp 这个 mod 下有4个 trait,另外两个是 Ord 和 Eq。 Rust 对于4个 trait 的处理是很明确的。

因为在浮点数有一个特殊的值叫 NaN,这个值表示未定义的一个浮点数。在 Rust 中可以用0.0f32 / 0.0f32来求得其值,这个数是一个都确定的值,但它表示的是一个不确定的数,那么NaN != NaN 的结果是啥?标准库告诉我们是 true。但这么写有不符合Eq定义里的total equal(每位一样两个数就一样)的定义。因此有了 PartialEq这么一个定义,NaN 这个情况就给它特指了。

为了普适的情况,Rust 的编译器就选择了PartialOrd 和PartialEq来作为其默认的比较符号的trait。

重载运算符

以上运算符都有在Rust中都有trait相对应。所以这些运算符都可以被重载

所以只要重新实现运算符的trait就可以实现运算符重载。

use std::ops::{Add, Sub};

#[derive(Copy, Clone)]
struct A(i32);

impl Add for A {
    type Output = A;
    fn add(self, rhs: A) -> A {
        A(self.0 - rhs.0)
    }
}

impl Sub for A {
    type Output = A;
    fn sub(self, rhs: A) -> A{
        A(self.0 + rhs.0)
    }
}

fn main() {
    let a1 = A(10i32);
    let a2 = A(5i32);
    let a3 = a1 + a2;
    println!("{}", (a3).0);
    let a4 = a1 - a2;
    println!("{}", (a4).0);
}

不可重载运算符

Rust中如下运算符不可被重载,所以也没有对应的trait。

借用运算符

&&mut:租借,borrow。向一个 owner 租借其使用权,分别租借一个只读使用权和读写使用权。

惰性 boolean 运算符

逻辑运算符有三个,分别是 &&、||和!。其中前两个叫做惰性 boolean 运算符,之所以叫这个名字,是因为在 Rust 中也会出现其他类 C 语言的逻辑短路问题,所以取了这么一个名字。其作用和 C 语言里的一模一样。不过不同的是,Rust 里这个运算符只能用在 bool 类型上。
在C++中,这三个运算符一般也是禁止重载的。

类型转换运算符

这个看起来并不算个运算符,因为它是个单词 as。就是类似于其他语言中的显示转换了。

fn avg(vals: &[f64]) -> f64 {
    let sum: f64 = sum(vals);
    let num: f64 = len(vals) as f64;
    sum / num
}

results matching ""

    No results matching ""