如何实现“添加"特征来引用结构? [英] How do I implement the Add trait for a reference to a struct?
问题描述
我制作了两个元素Vector
结构,并且想重载+
运算符.
I made a two element Vector
struct and I want to overload the +
operator.
我使所有函数和方法都采用引用而不是值,而且我希望+
运算符以相同的方式工作.
I made all my functions and methods take references, rather than values, and I want the +
operator to work the same way.
impl Add for Vector {
fn add(&self, other: &Vector) -> Vector {
Vector {
x: self.x + other.x,
y: self.y + other.y,
}
}
}
根据我尝试的变化,我会遇到生命周期问题或类型不匹配.具体来说,&self
参数似乎没有被视为正确的类型.
Depending on which variation I try, I either get lifetime problems or type mismatches. Specifically, the &self
argument seems to not get treated as the right type.
我在impl
和Add
上都看到了带有模板参数的示例,但是它们只会导致不同的错误.
I have seen examples with template arguments on impl
as well as Add
, but they just result in different errors.
我发现如何为不同的RHS类型和返回值重载运算符? /a>,但是即使我将use std::ops::Mul;
放在顶部,答案中的代码也无法正常工作.
I found How can an operator be overloaded for different RHS types and return values? but the code in the answer doesn't work even if I put a use std::ops::Mul;
at the top.
我每晚使用rustc 1.0.0(ed530d7a3 2015-01-16 22:41:16 +0000)
I am using rustc 1.0.0-nightly (ed530d7a3 2015-01-16 22:41:16 +0000)
我不会接受您只有两个字段,为什么要使用引用"作为答案;如果我想要一个100个元素的结构怎么办?我将接受一个答案,该答案表明即使是大型结构,如果是这种情况,我也应该按值传递(尽管我不这么认为.)我有兴趣了解结构大小的良好经验法则并按值和结构传递值,但这不是当前的问题.
I won't accept "you only have two fields, why use a reference" as an answer; what if I wanted a 100 element struct? I will accept an answer that demonstrates that even with a large struct I should be passing by value, if that is the case (I don't think it is, though.) I am interested in knowing a good rule of thumb for struct size and passing by value vs struct, but that is not the current question.
推荐答案
您需要在&Vector
而不是Vector
上实现Add
.
You need to implement Add
on &Vector
rather than on Vector
.
impl<'a, 'b> Add<&'b Vector> for &'a Vector {
type Output = Vector;
fn add(self, other: &'b Vector) -> Vector {
Vector {
x: self.x + other.x,
y: self.y + other.y,
}
}
}
在其定义中,Add::add
始终将self
作为值.但是引用的类型与其他任何 1 一样,因此它们也可以实现特征.在引用类型上实现特征时,self
的类型是引用;引用按值传递.通常,Rust中按值传递意味着转移所有权,但是当按值传递引用时,它们只是被复制(如果是可变引用,则被重新借入/移动),并且不会转移对引用者的所有权(因为引用首先不拥有其参照对象).考虑到所有这些,Add::add
(和许多其他运算符)按值取self
是有意义的:如果需要获取操作数的所有权,则可以直接在结构/枚举上实现Add
,如果否,您可以在引用上实现Add
.
In its definition, Add::add
always takes self
by value. But references are types like any other1, so they can implement traits too. When a trait is implemented on a reference type, the type of self
is a reference; the reference is passed by value. Normally, passing by value in Rust implies transferring ownership, but when references are passed by value, they're simply copied (or reborrowed/moved if it's a mutable reference), and that doesn't transfer ownership of the referent (because a reference doesn't own its referent in the first place). Considering all this, it makes sense for Add::add
(and many other operators) to take self
by value: if you need to take ownership of the operands, you can implement Add
on structs/enums directly, and if you don't, you can implement Add
on references.
在这里,self
的类型为&'a Vector
,因为这是我们要在其上实现Add
的类型.
Here, self
is of type &'a Vector
, because that's the type we're implementing Add
on.
请注意,我还为RHS
类型参数指定了不同的生存期,以强调两个输入参数的生存期无关的事实.
Note that I also specified the RHS
type parameter with a different lifetime to emphasize the fact that the lifetimes of the two input parameters are unrelated.
1 实际上,引用类型的特殊之处在于,您可以为包装箱中定义的类型实现对引用的特征(即,如果允许您为T
实现特征,那么您可以还允许将其用于&T
). &mut T
和Box<T>
具有相同的行为,但通常对于U<T>
而言并非如此,其中U
不在同一包装箱中定义.
1 Actually, reference types are special in that you can implement traits for references to types defined in your crate (i.e. if you're allowed to implement a trait for T
, then you're also allowed to implement it for &T
). &mut T
and Box<T>
have the same behavior, but that's not true in general for U<T>
where U
is not defined in the same crate.
这篇关于如何实现“添加"特征来引用结构?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!