0
fn get_str1<'a>() -> &'a str {
    let x = "hello";
    return x;
}

fn get_str2<'a>(str1: &str) -> &'a str {
    let x: &'a str = (str1.to_string() + "123").as_str();
    return x;
}

fn get_str3<'a>(str1: &str) -> &'a str {
    let tmp = str1.to_string() + "123";
    let x: &'a str = tmp.as_str();
    return x;
}

#[test]
fn lifetime_test() {
    println!("{}", get_str1());
    println!("{}", get_str2("hello"));
    println!("{}", get_str3("hello"))
}

当我调用时get_str1,它没有问题,但是当我调用时get_str2,它有一个编译错误:

error[E0597]: borrowed value does not live long enough
 --> src/main.rs:7:22
  |
7 |     let x: &'a str = (str1.to_string() + "123").as_str();
  |                      ^^^^^^^^^^^^^^^^^^^^^^^^^^         - temporary value only lives until here
  |                      |
  |                      temporary value does not live long enough
  |
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 6:1...
 --> src/main.rs:6:1
  |
6 | fn get_str2<'a>(str1: &str) -> &'a str {
  | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  = note: consider using a `let` binding to increase its lifetime

当我调用时get_str3,它也有一个编译错误:

error[E0597]: `tmp` does not live long enough
  --> src/main.rs:13:22
   |
13 |     let x: &'a str = tmp.as_str();
   |                      ^^^ borrowed value does not live long enough
14 |     return x;
15 | }
   | - borrowed value only lives until here
   |
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 11:1...
  --> src/main.rs:11:1
   |
11 | fn get_str3<'a>(str1: &str) -> &'a str {
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

为什么我会收到这些错误以及如何修复get_str2get_str3

4

1 回答 1

1

第一个函数有效,因为字符串具有'static生命周期并将由编译器提升。

至于其他..

fn get_str2<'a>(str1: &str) -> &'a str {
    let x = (str1.to_string() + "123").as_str();
    return x
}

这部分: str1.to_string(), 不是返回一个字符串切片......而是一个新的实例 a String。这与此基本相同:

let x = str1.to_string(); // this is of type String, and its lifetime is local to this function
let y = str1 + "123"; // This consumes str1 and appends a &str to it - thus the lifetime is still of the new String instance above
let z = y.as_str(); // This returns a reference to the local String instance

阅读上面的每条评论,很明显您实际上是在尝试返回对 local 的引用String。你不能这样做,因为String将在函数结束时被销毁,并且引用将无效。

这也适用于您的第三个功能。您正在返回对String将在函数结束时销毁的实例的引用。

于 2018-08-01T01:45:28.660 回答