Rust 的范围生命周期实际上意味着什么?

2023-12-21

So, in:

fn v1<'a> (a:~[&'a str]) -> ~[&'a str] {
  return a;
}

#[test]
fn test_can_create_struct() {
  let x = v1("Hello World".split(' ').collect());
}

我知道,我读过http://static.rust-lang.org/doc/master/guide-lifetimes.html#named-lifetimes http://static.rust-lang.org/doc/master/guide-lifetimes.html#named-lifetimes,但我不明白这段代码是什么实际上确实如此.

该函数基本上像通用 fn 一样参数化,但具有生命周期,这是我在 IRC 频道上看到的说法,但让我们想象一下情况是这样的,我们有一个 L,它是一些特定的生命周期结构。

显然我在隐含地调用:

v1::<L>("Hello World".split(' ').collect());

..但我不是。传递给该函数的生命周期是instance一生的一部分,它不是一生的一种类型,所以这个评论对我来说没有任何意义。

我的意思是,我基本上明白发生了什么(我认为):返回~[&str]与调用者的作用域具有相同的生命周期,大概是test_can_create_struct()功能。那是因为(据我所知)该功能v1随生命周期被调用instance来自调用函数。

很混乱。

然后我们还有其他一些例子,例如:https://gist.github.com/bvssvni/8970459 https://gist.github.com/bvssvni/8970459

这是一个片段:

impl<'a> Data<'a> {
  pub fn new() -> Data<'a> {
    Data { a: None, b: None }
  }

  pub fn a(&'a mut self, a: int) -> State<'a, Step1> {
    self.a = Some(a);
    State { data: self }
  }
}

现在我天真地认为Data<'a>意味着函数的生命周期实例a()是一样的。

即如果您创建一个Data (let blah = Data::new())并致电blah.a(),生命周期继承自create调用;即State只要父对象存在,返回的对象就会存在Data对象确实如此。

...但显然这也是错误的。所以我现在根本不知道生命周期变量意味着什么。

Help!


因此,回答这个问题最简单的方法就是退后一步,带你了解一生到底是什么。

让我们看一个简单的函数:

fn simple_function() {
  let a = MyFoo::new();
  println("{}", a);
}

在这个函数中,我们有一个变量,a。该变量与所有变量一样,存在一定的时间。在这种情况下,它会一直存在到函数末尾。当函数结束时,a死了。的寿命a,则可以描述为从函数的开头开始,在函数的末尾结束。

下一个函数将无法编译:

fn broken_function() -> &MyFoo {
  let a = MyFoo::new();
  return &a;
}

当你这样做时&a, 你是借用 a 参考 to a。然而,借钱的问题在于,你应该归还借来的东西。 Rust对此非常严格,不会让你有无法返回的引用。如果你借用的参考资料已经不存在了,你就无法归还参考资料,这样就不行了。

这对我们意味着什么broken_function是这样,因为a在函数结束时死亡,引用无法转义该函数,因为这会使其持久a.

下一步是这样的:

fn call_fn() {
  let a = MyFoo:new();
  {
    let a_ref = &a;
    let b = lifetimed(a_ref);

    println!("{}", *b);
  }
}

fn lifetimed<'a>(foo: &'a MyFoo) -> &'a MyBar {
   return foo.as_bar();
}

这里有两个函数,call_fn and lifetimed,这里发生了一些微妙的事情,所以我将对其进行分解。

In call_fn我首先创建一个新实例MyFoo并将其分配给a,那么,我借用一下参考a并将其分配给a_ref。借用的问题在于,当您进行借用时,生命周期信息将从您借用的变量传输到引用本身。所以现在a_ref,作为一个变量,有它自己的生命周期,它在该内部作用域的开始和结束处开始和结束,但是a_ref also有一生,从转移过来的a.

具体的生命周期无法命名,但让我们假装我们可以通过使用数字来做到这一点。如果生命周期为a is #1,那么type of a_ref is &'#1 MyFoo。当我们经过a_ref to lifetimed,编译器填写生命周期参数'a就像其他类型参数一样。lifetimed的返回类型是具有相同生命周期的引用,因此编译器会填充那里的空间。有效地进行独特的呼叫lifetimed(foo: &'#1 MyFoo) -> &'#1 MyBar.

这就是生命周期出现在类型参数列表中的原因,它们是类型系统的一部分,如果类型不匹配,则会出现错误。编译器会计算出函数编译所需的生命周期,因此您永远不必担心它,但也不会在当前函数之外查找以获取更多信息。您需要使用参数告诉编译器您正在调用的函数,以便编译器知道一切正常。


NB:您可以明确命名一个生命周期。'static这是在整个程序期间持续的事物的生命周期。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Rust 的范围生命周期实际上意味着什么? 的相关文章

随机推荐