我正在编写一个对两个数组进行分段乘法的函数。
xs.iter()
.zip(ys).map(|(x, y)| x * y)
.sum()
在其他一些语言中,我可以将(*)
作为函数传递给map
。 Rust有这个功能吗?
答案 0 :(得分:12)
NNN 是的。 Sorta有点不是。
您无法将运算符编写为名称。但是大多数运算符都有特征支持,并且可以写出这些特征的名称,因此a * b
实际上是Mul::mul(a, b)
,您可以将Mul::mul
作为函数传递指针。
但在这种情况下,这并没有帮助,因为Iterator::map
期待FnMut((A, B)) -> C
,而二元运算符都实现FnMut(A, B) -> C
。
现在,你可以为此编写一个适配器,但是你需要一个适用于arity和mutability的每个组合。 和你必须吃堆分配和间接或需要夜间编译器。
或者,您可以在扩展特征上编写自己的Iterator::map
版本,该特性为元组的迭代器接受更高的arity函数...再次,每个arity都有一个......
老实说,使用闭包更简单。
答案 1 :(得分:8)
Rust没有任何语法来传递中缀运算符,主要是因为它无论如何都是多余的。
在Rust中,每个运算符都映射到一个特征:*
映射到std::ops::Mul
特征,例如。
因此,直接使用*
应使用std::ops::Mul::mul
:
xs.iter().zip(ys).map(Mul::mul).sum();
然而,有几个困难:
Mul
是为普通值实现的,Mul::mul
期望两个参数xs.zip(ys)
产生一个元素(两个元素的元组)。所以,你需要从引用转到值,然后“解包”元组,并且...最终会缩短使用闭包。
答案 2 :(得分:3)
没有。 *
运算符已在std::Ops::Mul
中实现,但无法直接使用:
use std::ops::Mul::mul;
fn main() {
let v1 = vec![1, 2, 3];
let v2 = vec![1, 2, 3];
println!("{:?}", v1.iter().zip(v2).map(|(x, y)| mul).collect());
}
将导致以下错误:
error[E0253]: `mul` is not directly importable
--> <anon>:1:5
|
1 | use std::ops::Mul::mul;
| ^^^^^^^^^^^^^^^^^^ cannot be imported directly
您可以使用*
运算符介绍自己的函数,但不会增加很多值:)。