Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/performance/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Rust 传递给重载PartialEq的值的所有权_Rust_Operator Overloading_Ownership_Borrowing - Fatal编程技术网

Rust 传递给重载PartialEq的值的所有权

Rust 传递给重载PartialEq的值的所有权,rust,operator-overloading,ownership,borrowing,Rust,Operator Overloading,Ownership,Borrowing,我一直在玩弄重载一些操作符。我遇到了一个我不太明白的情况。当为我的structValue实现traitPartialEq时,我注意到下面的实现工作并且不移动值,允许我在对值使用=操作符后继续使用值,而不将值的引用传递到操作符中 另一方面,这不适用于Neg特性(或Add,Sub等)的实现。为了在不移动值的情况下使用-运算符,我必须在引用值结构时实现Neg特性 为什么我可以实现PartialEq特性而不必担心在不传递值引用时的移动,但是在实现Neg特性时我确实需要担心?我是否错误地实现了Neg特性?

我一直在玩弄重载一些操作符。我遇到了一个我不太明白的情况。当为我的struct
Value
实现trait
PartialEq
时,我注意到下面的实现工作并且不移动值,允许我在对值使用
=
操作符后继续使用值,而不将值的引用传递到操作符中

另一方面,这不适用于
Neg
特性(或
Add
Sub
等)的实现。为了在不移动值的情况下使用
-
运算符,我必须在引用
结构时实现
Neg
特性

为什么我可以实现
PartialEq
特性而不必担心在不传递值引用时的移动,但是在实现
Neg
特性时我确实需要担心?我是否错误地实现了
Neg
特性?我忽略了
PartialEq
这一特性的微妙之处吗

这是我的密码:

struct Value {
    x: i32
}

impl PartialEq for Value {
    fn eq(&self, other: &Value) -> bool {
        if self.x == other.x {
                true
            } else {
                false
            }
    }
}
impl Eq for Value {}

impl Neg for &Value {
    type Output = Value;

    fn neg(self) -> Self::Output {
        Value {
            x: -self.x
        }
    }
}

fn main() {
    let v1: Value = Value {x: 1};
    let v2: Value = Value {x: 2};
    let equal = v1 == v2; // Not passing a reference, but also able to use v1
    let v3 = -&v1;
    let v4 = -&v1; // Works because I am passing a reference. If I change the implementation of Neg to 'impl Neg for Value' and remove the reference here and in the line above (for v3), it will complain that v1 had been moved (as expected).
}
我忽略了
PartialEq
这一特性的微妙之处吗

PartialEq
的方法通过引用采用
self
other
&self
other:&T
在签名中),而
Neg
Add
Sub
等方法通过值采用
self
和(对于二进制运算符)
other
self
other:T
在签名中)。
v1==v2
desugars to
PartialEq::eq(&v1,&v2)
,而
!v1
desugars to
Neg::Neg(v1)

您可能希望
Neg
获得传递值的所有权的原因是,如果该值已分配动态内存(通过
Box
Vec
等)。在这种情况下,可能更有效的方法是变异
self
,然后返回
self
(或在
输出
类型不同于
自身
类型的情况下重用动态内存的另一个对象),而不是分配新对象(这将需要新的动态内存分配),即使操作后未使用原始值

另一方面,
PartialEq
的方法总是返回一个
bool
。一个
bool
不分配任何动态内存,因此按值传递参数没有好处。不希望测试两个对象是否相等需要对其中一个或两个对象进行变异,因此参数a重新共享引用

我是否错误地实现了
Neg
特性

不,但您可能要考虑对<代码>值和Value<代码>执行<代码> Neg <代码>(特别是如果您正在为他人编写一个库)


如果您的类型复制成本很低(即它很小,不使用动态内存),请考虑执行<代码>克隆< /COD>和<代码>复制< /代码>(可能通过派生它们)同样。通过这种方式,您可以将值传递给运算符,而无需将值移动到运算符,因为值将被复制。

如果您的结构很小,并且不需要任何特殊的复制逻辑(在这种情况下是克隆),您也可以实现
Copy