如何将返回值的生命周期设置为我移入其中的变量的生命周期?

sgl*_*div 8 rust

我试图教自己一些生锈,并写了一些看起来像:

let args:Vec<String> = env::args().collect();
let parsed = parser::sys(args.as_slice());
Run Code Online (Sandbox Code Playgroud)

...

pub fn sys<'a>(args:&'a [String]) -> Parsed<'a> {
  parsed(args)
}
Run Code Online (Sandbox Code Playgroud)

哪个parsed是解析和加载配置的函数.

这很好用.现在我试图抽象地在调用中显式调用env::args()和隐藏它sys,所以我写了一个新版本sys

pub fn sys<'a>() -> Parsed<'a> {
  let args:Vec<String> = env::args().collect();
  parsed(args.as_slice())
}
Run Code Online (Sandbox Code Playgroud)

这失败了:

error: `args` does not live long enough
src/test.rs:66      parsed(args.as_slice())
Run Code Online (Sandbox Code Playgroud)

我认为错误是因为编译器无法推断我希望这个新创建的结构的生命周期是我想要将其移入的变量的生命周期.它是否正确?如何在此返回值上注释生命周期/修复此问题?

Mat*_* M. 8

我认为错误是因为编译器无法推断我希望这个新创建的结构的生命周期是我想要将其移入的变量的生命周期。

实际上,没有。

错误是因为您试图创建对变量的引用,该引用args在您返回后将不再有效,sys因为它args是一个局部变量,因此在sys.

如果你想使用引用,你可以提供sys一个&'a mut Vec<String>(空),填写它sys,然后返回对它的引用:

pub fn sys<'a>(args: &'a mut Vec<String>) -> Parsed<'a> {
    *args = env::args().collect();
    parsed(args.as_slice())
}
Run Code Online (Sandbox Code Playgroud)

这保证argssys通话的寿命。这将args在结果的生命周期内借用。

另一种解决方案是取消'a并简单地拥有Parsed它的元素,而不是引用它们;但是没有定义Parsed我不能建议如何最好地这样做。