我正在尝试在 Rust 中实现一个基本的多项式类型,其中包含用于数学运算的重载运算符。到目前为止,我可以通过重载运算符来设法实现加法、减法等基本操作。问题是,我想通过引用来获取操作数以避免不必要的复制。 IE。 :
impl ops::Add for &Polynomial {
type Output = Polynomial;
fn add(self, other: Self) -> Polynomial {
let mut result = self.clone();
for (power, coeff) in other.coefficients.iter().enumerate() {
result.add_coeff(power, *coeff);
}
result
}
}
impl ops::Sub for &Polynomial {
// Implementation
// ...
}
impl ops::Mul for &Polynomial {
// Implementation
// ...
}
// Etc.
这按预期工作,但是它强制用户每次都明确地借用操作数,随着表达式变得更复杂,这变得更难读:
let (quotient, remainder) = p2.div_rem(&p1);
assert_eq!(&("ient * &p1) + &remainder, p2);
// Even worse example found on the internet.
// Note that you need to explicitly borrow each and every intermediate result :
let result = &(&(&a * &b) + &(&c * &d)) / 2;
除了最后两行,我认为如果我可以写的话会更清晰易读:
assert_eq!(quotient * p1 + remainder, p2);
let result = (a * b + c * d) / 2;
…让借用“自动”发生(就像你调用一个方法时所做的那样,它有一个 &self
作为任何值的第一个参数:它是自动和隐式借用的,而不必明确借用它)。
但是我不知道是否可以做,或者怎么做?
最佳答案
AFAIK,不,没有简单的方法来做到这一点,因为 Rust 引用总是显式的,从不隐式的,由于两种设计选择(即避免 C++ 引用的相同设计问题,这很奇怪 ) 和必要性(由于借用检查器)。
T, &T, &mut T, *const T
, ... 都是不同的类型具有不同的语义,所以允许 impl ops::Add for &Polynomial
也适用于 Polynomial
基本上意味着 impl ops::Add for &T
将自动实现 ops::Add
for T
,这可能会导致非常奇怪且可能不安全的结果,特别是如果相反的情况也是如此。那么 &mut
呢? &mut T
会自动衰减为 &
,对借用本身的生命周期有何影响?
此外,在非 Copy
值类型上实现 ops::Add
非常奇怪,因为运算符随后导致其操作数被移入 - 这绝对是这不是人们在大多数情况下使用 +
时所期望的。
关于rust - (Rust) 有没有办法为重载的运算符自动借用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67457210/