[英]Why can I add a String and a reference, but not two Strings? (E0308: Mismatched types)
I'm trying to write a trait on the String
type that will allow it to concatenate Bar
to any other string.我正在尝试在
String
类型上编写一个特征,以允许它将Bar
连接到任何其他字符串。
I know what the solution is but I'm not sure why it works.我知道解决方案是什么,但我不确定它为什么会起作用。 Could someone please explain the theory underlying the syntax for me?
有人可以为我解释一下语法背后的理论吗?
// problematic code
// error[E0308]: mismatched types
// rustc --explain E0308
fn append_bar(self) -> String {
self + String::from("Bar")
}
// solution
fn append_bar(self) -> String {
self + &String::from("Bar")
}
The full script is below.完整的脚本如下。
trait AppendBar {
fn append_bar(self) -> String;
}
impl AppendBar for String {
fn append_bar(self) -> String {
self + String::from("Bar")
}
}
fn main() {
let s = String::from("Foo");
let s = s.append_bar();
println!("s: {}", s);
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn is_FooBar() {
assert_eq!(String::from("Foo").append_bar(), String::from("FooBar"));
}
#[test]
fn is_BarBar() {
assert_eq!(
String::from("").append_bar().append_bar(),
String::from("BarBar")
);
}
}
The +
operator is sugar for the add
method of the std::ops::Add
trait, and the implementation for String
is: +
运算符是std::ops::Add
trait 的add
方法的糖, String
的实现是:
impl<'_> Add<&'_ str> for String {
type Output = String;
fn add(mut self, other: &str) -> String {
self.push_str(other);
self
}
}
That is, the right hand side of the +
must be &str
when the left hand side is a String
.也就是说,当左侧是
String
时, +
的右侧必须是&str
。
However, due to deref coercion for function arguments, you can also pass a &String
instead of a &str
, because String
implements Deref<Target = str>
.但是,由于function arguments的 deref 强制,您也可以传递
&String
而不是&str
,因为String
实现Deref<Target = str>
。
It's worth noting that a better "fix" for the exact code you provided is to avoid allocating a temporary String
altogether, since "Bar"
is already a &str
:值得注意的是,对于您提供的确切代码,更好的“修复”是避免完全分配临时
String
,因为"Bar"
已经是&str
:
fn append_bar(self) -> String {
self + "Bar"
}
See also: Why is it discouraged to accept a reference to a String (&String), Vec (&Vec), or Box (&Box) as a function argument?另请参阅: 为什么不鼓励接受对字符串 (&String)、Vec (&Vec) 或框 (&Box) 的引用作为 function 参数?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.