これ Rustチュートリアルは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。
_+=
_が問題であることはすでにわかっていますが、もう少し詳しく説明したいと思います。
あなたの場合、fold
クロージャーに提供される引数は__
_および_&u32
_です。最初のタイプは、まだ指定されていない整数です。フォールドコールを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`
_
ここから、couldcould(-===-)としてsum
を変更可能としてマークしますが、正しい解決策は_sum + val
_で単純にフォールドすることです発見されました。
Rustの新しいバージョンでは、 sum
イテレータを直接使用して、fold
をスキップすることもできます。
_let sum: u32 = vec![1,2,3,4,5,6].iter().sum();
_
私が書いたように、私のコードには大きな違いがあることがわかりました
sum += x
の代わりに
sum + x
。
少なくとも、誰かが同様の状況に陥った場合に、この質問が役立つことを願っています。