首页 文章

Rust中的参考文献

提问于
浏览
2

我尝试理解Rust中的借用机制和引用,因此我创建了以下小例子:

extern crate core;

use core::fmt::Debug;

#[derive(Copy, Clone)]
pub struct Element(pub (crate) [u8; 5]);

impl Debug for Element {
    fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {
        write!(f, "Element({:?})", &self.0[..])
    }
}

impl Element {
    fn one() -> Element {
        Element([1, 1, 1, 1, 1])
    }
    fn double(&self) -> Element {
        let mut result = *self;
        for i in 0..5 { result.0[i] = 2*result.0[i]; }
        result
    }
    fn mut_double(&mut self) -> Element {
      for i in 0..5 { self.0[i] = 2*self.0[i]; }
      *self
    }
}

fn main() {
  let mut a = Element::one();
  println!("a = {:?}", a); // a = Element([1, 1, 1, 1, 1])
  a = a.double();
  println!("a = {:?}", a); // a = Element([2, 2, 2, 2, 2])
  a = (&a).double();
  println!("a = {:?}", a); // a = Element([4, 4, 4, 4, 4])
  a = a.mut_double();
  println!("a = {:?}", a); // a = Element([8, 8, 8, 8, 8])
  a = (&mut a).mut_double();
  println!("a = {:?}", a); // a = Element([16, 16, 16, 16, 16])
}

所以,上面的代码可以工作,但是在调用 double 方法时我会感到困惑 . 如您所见,它被定义为 fn double(&self) -> Element ,因此它基本上采用不可变引用 . 现在在main中,我创建一个名为 a 的新 Element 变量,然后在其上调用 double 方法两次 . 我第一次做 a.double() ,第二次 (&a).double() . 它们似乎都正常工作,但我不明白为什么第一次调用 a.double() 是有效的,编译器不会抱怨它 . 由于 a 的类型为 Element ,而不是类型 &Element ,显然 double 方法要求 &Element ,所以关于引用 . mut_double 方法也会发生同样的事情 . 为什么在分别调用 doublemut_double 方法时不必指定 (&a)(&mut a) ?在Rust的引擎盖下发生了什么?

1 回答

  • 4

    简短:语言就是这样,因为它更方便 .

    很长(extract from the bookemphasis 是我的):

    哪里是 - >运营商?在像C这样的语言中,两个不同的运算符用于调用方法:您使用 . 如果你直接在对象上调用方法,那么 - >如果你在指向对象的指针上调用方法,并且需要首先取消引用指针 . 换句话说,如果object是一个指针,object-> something()类似于(* object).something() . Rust没有 - >运算符的等价物;相反,Rust有一个称为自动引用和解除引用的功能 . 调用方法是Rust中具有此行为的少数几个地方之一 . 以下是它的工作原理:当您使用object.something()调用方法时,Rust会自动添加&,&mut或*,因此对象匹配方法的签名 . 换句话说,以下是相同的:p1.distance(&p2);
    (P1).distance(P2);
    第一个看起来更干净 . 这种自动引用行为是有效的,因为方法有一个明确的接收器 - 自我类型 . 鉴于方法的接收者和名称,Rust可以明确地确定该方法是读取(&self),变异(&mut self)还是消费(self) . Rust为方法接收器隐含借用这一事实是在实践中使所有权符合人体工程学的重要部分 .

相关问题