Rust 07: 生命周期标注(‘a, ‘static)

所有权机制回顾

先来回顾一下前面的内容:

  1. Rust的单一所有权机制,让编译器能够准确跟踪所有者的作用域,从而在在所有者超出作用域的时候进行值内存的释放。
  2. 在同一作用域之下,编译器能够准确判断所有借用(borrow)的使用情况,保证借用的生命周期不会超过值本身的生命周期。

为何需要生命周期标注

尽管单一所有权机制能妥善处理大部分情况。但是,如果将借用(引用)作为函数返回值类型的时候,编译器就不干了:因为缺少足够的信息,无法判断返回的借用是否仍然有效,如果有效那么到何时失效的问题
也就是说,编译器缺少被借用的值的生命周期信息。

 fn max1(x: &i32, y: &i32) -> &i32 {
     if x>y {x} else {y}
 }

上面的代码编译会报错:缺少具名的生命周期参数

fn max1(x: &i32, y: &i32) -> &i32 {
           ----     ----     ^ expected named lifetime parameter

如何标注生命周期

对于返回借用类型缺少生命周期的问题解决,Rust的做法是,对函数返回值进行生命周期参数标注
返回的借用的生命周期,要么由输入参数的生命周期来标定,要么就是全局静态的(在整个程序运行期间有效),即'static
Rust中生命周期参数的格式为:'1到多个小写字母
比如,'a'input都是合法的生命周期参数。

输出依赖于输入参数的生命周期
// 输入的两个引用参数具有相同的生命周期参数'a,返回的引用也是
fn max2<'a>(x: &'a i32, y: &'a i32) -> &'a i32 {
    if x>y {x} else {y}
}
println!("{}", max2(&13,&19));//19
输出为’static
fn lifetime1() -> &'static str { 
    // 字符串字面量位于ROData区,生命周期是全局静态的
    // 详见https://blog.csdn.net/linysuccess/article/details/123765834
    let name = "Hello";
    // 返回字符串切片
    &name[1..]
}

struct中引用类型的标注

写个小例子吧:

struct TreeNode1<'a> {
    val: i32,
    left: Option<&'a TreeNode1<'a>>,
    right: Option<&'a TreeNode1<'a>>,
}

编译器自动标注

事实上,所有引用参数、引用返回值都需要生命周期标注,那为什么很多函数的参数或者返回值都使用了引用,编译器却没有提示我要额外标注生命周期呢?
答案是,编译器会通过一些简单的规则为函数自动添加标注:

  1. 所有引用类型的参数都有独立的生命周期 'a 、'b 等
  2. 如果只有一个引用型输入,它的生命周期会赋给所有输出
  3. 如果有多个引用类型的参数,其中一个是 self,那么它的生命周期会赋给所有输出

总结

函数的引用参数和引用返回值需要生命周期参数进行标注,帮助编译器建立和编译时检查引用之间的生命周期约束关系。
返回引用的生命周期,需要依赖于输入参数的生命周期,或者是整个程序的运行周期(即:静态生命周期'static)。
编译器根据几条简单的规则对常见情况的引用参数自动进行标注,减轻开发者的负担。

  • 9
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值