生命周期如何作用于常量字符串/字符串文字?

How does the lifetime work on constant strings / string literals?

我阅读了 tutorial on the official website,我对常量字符串/字符串文字的生命周期有一些疑问。

我在编写以下代码时遇到错误:

fn get_str() -> &str {
    "Hello World"
}

错误:

error[E0106]: missing lifetime specifier
 --> src/main.rs:1:17
  |
1 | fn get_str() -> &str {
  |                 ^ expected lifetime parameter
  |
  = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from
  = help: consider giving it a 'static lifetime

不过我加个参数就OK了:

fn get_str(s: &str) -> &str {
    "Hello World"
}

为什么这行得通? "Hello World" 如何借用参数 s,即使它与 s 无关?

Lifetime elision 推断出

的完整类型
fn get_str(s: &str) -> &str

fn get_str<'a>(s: &'a str) -> &'a str

这基本上意味着只要 s 有效,get_str 的 return 值就必须有效。 string literal "Hello world" is &'static str 的实际类型,这意味着它对整个 运行 程序有效。由于这满足了函数签名中的生命周期限制(因为 'static 总是包含 'a 用于任何 'a),所以这是可行的。

但是,让您的原始代码正常工作的更明智的方法是为函数类型添加显式生命周期:

fn get_str() -> &'static str {
    "Hello World"
}

How does "Hello World" borrow from the parameter s, even it has nothing to do with s?

只有两个选项对具有单个引用参数的函数中的 return 值的生命周期有意义:

  1. 它可以是 'static,在您的示例中应该是,或者
  2. return 值的生命周期必须与参数的生命周期相关联,这是生命周期省略的默认设置。

在 post 顶部的 link 中选择后者是有一定道理的,但基本上可以归结为后者是更常见的情况。请注意,生命周期省略 根本不查看函数体 ,它只是通过函数签名。这就是为什么它不会考虑您只是 return 考虑字符串常量这一事实。