Rust:生命周期标注(lifetime annotation)
Rust語言中的所有引用(referrence)都有一個lifetime,指得是該引用有效的作用域(scope)。通常情況下,lifetime都是隱式的,rust編譯器會根據一些簡單的規則自己推斷。但在一些復雜情況下,編譯器無法準確的判斷引用的生命周期,則需要我們手動標注lifetime。
比如寫一個返回最長字符串的函數,像下面這么寫就通不過編譯。因為函數返回值也是引用,但又因為我們有兩個引用作為輸入參數,而rust在編譯的時候不知道返回誰,也就無法確認函數返回值的生命周期。
fn longest(x: &str, y: &str) -> &str {if x.len() > y.len() {x} else {y} } error[E0106]: missing lifetime specifier--> src/main.rs:1:33| 1 | fn longest(x: &str, y: &str) -> &str {| ^ expected lifetime parameter|= help: this function's return type contains a borrowed value, but the signature does not say whether it is borrowed from `x` or `y`?
生命周期標注
生命周期標注就是為了在上面這種情況下告訴Rust編譯器,函數返回值的生命周期是怎么樣的。生命周期的標注語法如下,一個生命周期變量可以用‘+一個或幾個小寫字母表示(比如?‘a ,’abc),生命周期變量放在引用符號 & 與引用名稱之前。
&i32 // a reference &'a i32 // a reference with an explicit lifetime &'a mut i32 // a mutable reference with an explicit lifetime用生命周期標注改寫上述函數?
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {if x.len() > y.len() {x} else {y} }上面的代碼里,我們用一個生命周期變量‘a (其實你可以認為這是一種標簽)同時標注了兩個參數以及返回值,來告訴Rust編譯器這三者的生命周期是一樣的。雖然這不一定是對的,因為這兩個輸入參數的生命周期實際上有可能是不一樣的,但是可以讓Rust編譯器暫時這么理解。因為標注的重點其實在于,告訴Rust編譯器你可以用x或者y的生命周期來當作函數返回值的生命周期。
因為x和y的生命周期有可能不一樣,所以函數返回值的生命周期實際上是由兩個參數里生命周期較短的那個決定的。
fn main() {let string1 = String::from("long string is long");let result;{let string2 = String::from("xyz");result = longest(string1.as_str(), string2.as_str());} // 1println!("The longest string is {}", result); //2 } error[E0597]: `string2` does not live long enough--> src/main.rs:15:5| 14 | result = longest(string1.as_str(), string2.as_str());| ------- borrow occurs here 15 | }| ^ `string2` dropped here while still borrowed 16 | println!("The longest string is {}", result); 17 | }| - borrowed value needs to live until here上述代碼里,函數返回值result的生命周期就由生命周期較短的string2決定。由于string2的生命周期在1處已經結束了,所以2處不可以在使用result這一函數返回值。
總結
以上是生活随笔為你收集整理的Rust:生命周期标注(lifetime annotation)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 头条:每6个中国人就有1个中招的!
- 下一篇: sg-uap mysql_SG-UAP常