生命周期如何处理常量字符串/字符串文字?

Posted

技术标签:

【中文标题】生命周期如何处理常量字符串/字符串文字?【英文标题】:How does the lifetime work on constant strings / string literals? 【发布时间】:2015-09-22 16:46:31 【问题描述】:

我阅读了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无关?

【问题讨论】:

【参考方案1】:

Lifetime elision 推断完整类型

fn get_str(s: &str) -> &str

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

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

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

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

“Hello World”如何借用s参数,甚至与s无关?

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

    可以是'static,就像在您的示例中一样,或者 返回值的生命周期必须与参数的生命周期相关联,这是生命周期省略的默认值。

在这篇文章顶部的链接中选择后者有一些理由,但基本上归结为后者是更常见的情况。请注意,生命周期省略根本不查看函数体,它只是通过函数签名。这就是为什么它不会考虑您只是返回一个字符串常量这一事实。

【讨论】:

@MatthieuM。感谢您的编辑。我真的应该在发布之前编译我的代码。 恕我直言,应用一些简单的生命周期省略规则与“推理”没有任何关系,这就是为什么我不会在这种情况下使用这个词。

以上是关于生命周期如何处理常量字符串/字符串文字?的主要内容,如果未能解决你的问题,请参考以下文章

如何处理 Template Toolkit 中包含非法标识符字符的哈希键?

C中字符串文字的“生命周期”

函数返回的字符串文字的生命周期

3.1 启动 Activity

如何清理 Maven 插件绑定?

用户可以撤销(运行时)权限的所有情况是啥? (在活动生命周期中)