无法使用 if 表达式附加到字符串而不是 if 语句
Unable to use if expression to append to string instead of if statement
我有以下代码可以正常工作:
fn main() {
let mut example = String::new();
if 1 + 1 == 2 {
example += &"string".to_string()
} else {
example += &'c'.to_string()
};
println!("{}", example);
}
当我将代码更改为:
fn main() {
let mut example = String::new();
example += if 1 + 1 == 2 {
&"string".to_string()
} else {
&'c'.to_string()
};
println!("{}", example);
}
我收到以下错误:
error[E0597]: borrowed value does not live long enough
--> src/main.rs:5:10
|
5 | &"string".to_string()
| ^^^^^^^^^^^^^^^^^^^^ temporary value does not live long enough
6 | } else {
| - temporary value dropped here while still borrowed
7 | &'c'.to_string()
8 | };
| - temporary value needs to live until here
error[E0597]: borrowed value does not live long enough
--> src/main.rs:7:10
|
7 | &'c'.to_string()
| ^^^^^^^^^^^^^^^ temporary value does not live long enough
8 | };
| - temporary value dropped here while still borrowed
|
= note: values in a scope are dropped in the opposite order they are created
这对我来说毫无意义,因为这两个片段看起来完全相同。为什么第二个代码段不起作用?
当您将 &
应用于表达式时,Rust 会自动创建拥有表达式计算结果的匿名变量。所以,你的代码大致相当于
fn main() {
let mut example = String::new();
example += if 1 + 1 == 2 {
let temp1 = "string".to_string();
&temp1
} else {
let temp2 = 'c'.to_string();
&temp2
};
println!("{}", example);
}
正如您现在希望清楚地看到的那样,temp1
的范围(和生命周期)仅限于 if
表达式的 true
分支,并且范围temp2
的表达式仅限于 if
表达式的 false
分支。范围/生存期都没有超出 if
表达式,因此 if
两个分支内的 String
不能附加到 example
.
与此相反,您的第一个示例大致相当于
fn main() {
let mut example = String::new();
if 1 + 1 == 2 {
let temp1 = "string".to_string();
example += &temp1;
} else {
let temp2 = 'c'.to_string();
example += &temp2;
};
println!("{}", example);
}
并且在这两种情况下,temp1
和 temp2
都存在足够长的时间,因此可以复制 String
的内容并在 [=13= 之前附加到 example
] 和 temp2
被丢弃。
你 。下面是一些有效的代码,并且更接近您的目标:
example += &if 1 + 1 == 2 {
"string".to_string()
} else {
'c'.to_string()
};
我不会声称这是惯用的 Rust。让我印象深刻的一件事是 "string"
被不必要地分配到 String
中。我会使用 String::push_str
and String::push
:
编写此代码
if 1 + 1 == 2 {
example.push_str("string");
} else {
example.push('c');
}
如果您不附加字符串,我会直接计算它:
let example = if 1 + 1 == 2 {
"string".to_string()
} else {
'c'.to_string()
};
我什至可能会使用动态调度(尽管不太可能):
let s: &std::fmt::Display = if 1 + 1 == 2 { &"string" } else { &'c' };
let example = s.to_string();
或
use std::fmt::Write;
let mut example = String::new();
let s: &std::fmt::Display = if 1 + 1 == 2 { &"string" } else { &'c' };
write!(&mut example, "{}", s).unwrap();
另请参阅:
我有以下代码可以正常工作:
fn main() {
let mut example = String::new();
if 1 + 1 == 2 {
example += &"string".to_string()
} else {
example += &'c'.to_string()
};
println!("{}", example);
}
当我将代码更改为:
fn main() {
let mut example = String::new();
example += if 1 + 1 == 2 {
&"string".to_string()
} else {
&'c'.to_string()
};
println!("{}", example);
}
我收到以下错误:
error[E0597]: borrowed value does not live long enough
--> src/main.rs:5:10
|
5 | &"string".to_string()
| ^^^^^^^^^^^^^^^^^^^^ temporary value does not live long enough
6 | } else {
| - temporary value dropped here while still borrowed
7 | &'c'.to_string()
8 | };
| - temporary value needs to live until here
error[E0597]: borrowed value does not live long enough
--> src/main.rs:7:10
|
7 | &'c'.to_string()
| ^^^^^^^^^^^^^^^ temporary value does not live long enough
8 | };
| - temporary value dropped here while still borrowed
|
= note: values in a scope are dropped in the opposite order they are created
这对我来说毫无意义,因为这两个片段看起来完全相同。为什么第二个代码段不起作用?
当您将 &
应用于表达式时,Rust 会自动创建拥有表达式计算结果的匿名变量。所以,你的代码大致相当于
fn main() {
let mut example = String::new();
example += if 1 + 1 == 2 {
let temp1 = "string".to_string();
&temp1
} else {
let temp2 = 'c'.to_string();
&temp2
};
println!("{}", example);
}
正如您现在希望清楚地看到的那样,temp1
的范围(和生命周期)仅限于 if
表达式的 true
分支,并且范围temp2
的表达式仅限于 if
表达式的 false
分支。范围/生存期都没有超出 if
表达式,因此 if
两个分支内的 String
不能附加到 example
.
与此相反,您的第一个示例大致相当于
fn main() {
let mut example = String::new();
if 1 + 1 == 2 {
let temp1 = "string".to_string();
example += &temp1;
} else {
let temp2 = 'c'.to_string();
example += &temp2;
};
println!("{}", example);
}
并且在这两种情况下,temp1
和 temp2
都存在足够长的时间,因此可以复制 String
的内容并在 [=13= 之前附加到 example
] 和 temp2
被丢弃。
你
example += &if 1 + 1 == 2 {
"string".to_string()
} else {
'c'.to_string()
};
我不会声称这是惯用的 Rust。让我印象深刻的一件事是 "string"
被不必要地分配到 String
中。我会使用 String::push_str
and String::push
:
if 1 + 1 == 2 {
example.push_str("string");
} else {
example.push('c');
}
如果您不附加字符串,我会直接计算它:
let example = if 1 + 1 == 2 {
"string".to_string()
} else {
'c'.to_string()
};
我什至可能会使用动态调度(尽管不太可能):
let s: &std::fmt::Display = if 1 + 1 == 2 { &"string" } else { &'c' };
let example = s.to_string();
或
use std::fmt::Write;
let mut example = String::new();
let s: &std::fmt::Display = if 1 + 1 == 2 { &"string" } else { &'c' };
write!(&mut example, "{}", s).unwrap();
另请参阅: