【问题标题】:How do I sum a vector using fold?如何使用折叠对向量求和?
【发布时间】:2015-04-09 20:55:45
【问题描述】:

ThisRust 教程很好地解释了fold() 机制,以及这个示例代码:

let sum = (1..4).fold(0, |sum, x| sum + x);

按预期工作。

我想在向量上运行它,所以基于那个例子,我首先写了这个:

let sum: u32 = vec![1,2,3,4,5,6].iter().fold(0, |sum, val| sum += val);

抛出错误:

error: binary assignment operation `+=` cannot be applied to types `_` and `&u32` [E0368]
let sum = ratings.values().fold(0, |sum, val| sum += val);
                                              ^~~~~~~~~~

我猜这可能是由于某种原因与引用相关的错误,所以我将其更改为fold(0, |sum, &val| sum += val),从而导致

error: mismatched types:
expected `u32`,
   found `()`

嗯,也许关闭有问题?使用{sum += x; sum },我得到了

binary assignment operation `+=` cannot be applied to types `_` and `&u32`

再次。

经过进一步的试验和错误,将mut 添加到sum 工作:

let sum = vec![1,2,3,4,5,6].iter().fold(0, |mut sum, &x| {sum += x; sum});

有人可以解释为什么向量的fold() 与教程有很大不同的原因吗?或者有没有更好的方法来处理这个问题?

作为参考,我使用的是 Rust beta,2015-04-02。

【问题讨论】:

  • 您将sum + x 替换为sum += x,带来了很大的不同。
  • 我不敢相信,我怎么会错过...谢谢!

标签: vector rust


【解决方案1】:

从Rust 1.11开始,你可以直接sum迭代器,跳过fold

let sum: u32 = vec![1, 2, 3, 4, 5, 6].iter().sum();

您已经发现+= 是问题所在,但我想提供更多说明。

在您的情况下,提供给fold 闭包的参数是_&u32。第一种类型是尚未指定的整数。如果您将 fold 调用更改为 fold(0u32, |sum, val| sum += val),您将收到稍有不同的消息:

let sum: u32 = vec![1,2,3,4,5,6].iter().fold(0u32, |sum, val| sum += val);
error[E0308]: mismatched types
  |
2 |     let sum: u32 = vec![1,2,3,4,5,6].iter().fold(0u32, |sum, val| sum += val);
  |                                                                          ^^^ expected u32, found &{integer}
  |
  = note: expected type `u32`
  = note:    found type `&{integer}`

二进制赋值运算+=的结果值为(),单位类型。这解释了当您更改为fold(0, |sum, &val| sum += val) 时的错误消息:

let mut a = 1;
let what_am_i = a += 1;
println!("{:?}", what_am_i); // => ()

如果您更改为fold(0, |sum, &val| {sum += val ; sum}),则会收到关于不可变变量的可理解错误:

let sum: u32 = vec![1,2,3,4,5,6].iter().fold(0, |sum, &val| {sum += val; sum});
error[E0384]: re-assignment of immutable variable `sum`
 --> src/main.rs:2:66
  |
2 |     let sum: u32 = vec![1,2,3,4,5,6].iter().fold(0, |sum, &val| {sum += val; sum});
  |                                                      ---         ^^^^^^^^^^ re-assignment of immutable variable
  |                                                      |
  |                                                      first assignment to `sum`

从这里,您可以sum 标记为可变,但正确的解决方案是简单地使用sum + val 折叠,正如您发现的那样。

【讨论】:

    【解决方案2】:

    事实证明,正如我所写的那样,我的代码存在巨大差异

    sum += x
    

    而不是

    sum + x
    

    好吧,至少我希望这个问题有所帮助,以防有人遇到类似情况。

    【讨论】:

      猜你喜欢
      • 2014-09-03
      • 1970-01-01
      • 2017-04-11
      • 2021-03-05
      • 2021-07-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多