美文网首页
rust 中的生命周期

rust 中的生命周期

作者: 西门早柿 | 来源:发表于2021-01-25 22:44 被阅读0次

    rust 中的生命周期是 rust 特有的一个概念,用于标识一个变量的生命长度。

    不能访问一个超出其生命周期的变量。我们可以用 {} 来显式的标识生命周期。

    'a{
      let a = 1;
      let b = 2;
      'b{
        b
      }
      //编译失败,变量 b 的生命周期已经结束。
      println!("b is {}", b);
    }
    

    代码中变量 a 的生命周期为 'a,变量 b 的生命周期为 'b,a 活的比 b 要长。

    这种情况下编译器可以明确的知道变量的生命周期边界,是不需要标注生命周期参数的。

    那么什么情况下需要标注生命周期参数呢?

    情况一,函数返回引用。
    fn larger_str(a: &str, b: &str) -> &str {
      if a > b {
        return a;
      }
      b
    }
    
    fn main() {
      let a = String::from("hello");
      let b = String::from("world");
      let c = larger_str(&a, &b);
      {
        b
      }
      //无法编译,编译器无法判断现在的 c 是否还是一个有效的引用。
      println!("c is {}", c);
    }
    

    正常情况下,编译时是不会知道函数的运行结果的,因此上面代码中编译器是不知道 c 最终指向的是 a 还是 b,因此无法判断 c 是否还是一个有效的引用。

    显然这种情况下 c 的生命周期取决于 ab 中生命周期较小的那一个。那么如何在代码里标识这种情况呢?

    fn larger_str<'a>(a: &'a str, b: &'a str) -> &'a str {
      if a > b {
        return a;
      }
      b
    }
    
    情况二,结构体中的引用
    struct Foo {
        a: &str,
        b: String,
    }
    
    fn main() {
        let s = String::from("hello");
        let f = Foo{a: &s, b: String::from("world")};
        //编译失败,编译器无法确定结构体中的引用是否还有效。
        println!("foo is {}", f.b);
    }
    

    因此,需要加上生命周期参数,标识结构体内的引用不能小于结构体的生命周期。如下所示。

    struct Foo<'a> {
        a: &'a str,
        b: String,
    }
    
    fn main() {
        let s = String::from("hello");
        let f = Foo{a: &s, b: String::from("world")};
        //编译失败,编译器无法确定结构体中的引用是否还有效。
        println!("foo is {}", f.b);
    }
    

    相关文章

      网友评论

          本文标题:rust 中的生命周期

          本文链接:https://www.haomeiwen.com/subject/awunzktx.html