ループとその解でのC#lambdaの発現キャプチャ
を理解する ループ内のLambda式は、一般的な落とし穴を示します。それらは同じ変数をキャプチャし、予期しない結果につながります。 これは、ラムダの式が、その作成時に変数の値をキャプチャしないのではなく、変数自体への参照をキャプチャしないために発生します。 この例を考えてみましょう:
予想出力(0、2、4、6、8)の代わりに、コードは5 8秒出力します。これは、すべてのlambda式が、各ラムダが作成された時点での値ではなく、<code class="language-csharp">List<Func<int>> actions = new List<Func<int>>(); int variable = 0; while (variable < 5) { actions.Add(() => variable * 2); ++variable; } foreach (var act in actions) { Console.WriteLine(act.Invoke()); }</code>
値(ループが完了した後10)の値を参照するためです。
ソリューション:コピーの作成variable
さて、各ラムダ式は異なる変数をキャプチャし、正しい出力をもたらします。
c#5以降:foreach and catvs
<code class="language-csharp">List<Func<int>> actions = new List<Func<int>>(); int variable = 0; while (variable < 5) { int copy = variable; // Create a copy actions.Add(() => copy * 2); ++variable; }</code>
ループの動作が変更されました。 コンパイラは、「閉鎖割り当ての一時変数」(CATV)を使用して、各反復に対して個別の変数を自動的に作成し、手動コピーの必要性を排除します。 この簡素化により、コードがよりクリーンになり、読みやすくなります。 ただし、copy
ループの例では、明示的なコピーが必要です。
以上がループのC#Lambda式が同じ変数をキャプチャするのはなぜですか?これを解決するにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。