13

重複の可能性:
C# の foreach と機能的な each

これは読みやすさのためのコーディングに関する質問です。

マスクする必要がある機密情報を含む要素の名前XDocumentList<string>名前があります (この例ではアンダースコアに置き換えます)。

XDocument xDoc;
List<string> propertiesToMask;

これは、従来のforeachループを使用.ForEachする方法と、lamba 構文のメソッドを使用する方法の 2 つの方法で記述できます。

foreach (string propertyToMask in propertiesToMask)
{
    foreach (XElement element in xDoc.Descendants(propertyToMask))
    {
        element.SetValue(new string('_', element.Value.Length));
    }
}

また

propertiesToMask
    .ForEach(propertyToMask => xDoc.Descendants(propertyToMask).ToList()
        .ForEach(element => element.SetValue(new string('_', element.Value.Length))));

どのアプローチが最も読みやすいと思いますか?その理由は? 2 番目の例を好む場合、読みやすくするためにどのように表示しますか?

4

6 に答える 6

14

これについては、Eric Lippert のブログに良いエントリがあります。要約すると、 によって実行されるタスクForEachは、C# の関数型プログラミング スタイルでは望ましくない副作用を生成することです。

于 2010-02-09T16:15:13.297 に答える
14
foreach (string propertyToMask in propertiesToMask)
{
    foreach (XElement element in xDoc.Descendants(propertyToMask))
    {
        element.SetValue(new string('_', element.Value.Length));
    }
}

間隔があるため、スキャンが非常に簡単になります。2番目は雑然としていて、実際に読まなければなりません。

于 2010-02-09T16:15:50.037 に答える
4

従来の方法には、簡単にデバッグできるという大きな利点があります。しかし、私は個人的ForEach()にこの場合のアプローチを好みます。流暢に書かれたコードをデバッグするのが難しいという状況は、コーディングスタイルではなく、利用可能なツールの欠陥であると私は考えています。私の個人的な経験では、そのような方法のエラー率は非常に低いので、それほど大きな問題ではありません。

次のコードを生成するいくつかの拡張メソッドを記述します。

propertiesToMask
   .SelectMany(property => document.Descendants(property))
   .ForEach(element => element.MaskValue());
于 2010-02-09T16:24:25.403 に答える
4

3 つの理由から、私は前者を強く好みます。

第一に、より効率的です (第二に、追加の ToList() 呼び出しがあります)。

第二に、私の意見では、より読みやすいです。

最後に、このテーマに関する Eric Lippert のブログ投稿を読むことをお勧めします。 避けるべき哲学的な理由がありますList<T>.ForEach。これは、機能的なスタイルを持っていても、副作用を引き起こすことが全体の目的であるためです。

于 2010-02-09T16:17:18.860 に答える
1

最初のものは、デバッガーの実行中に変更でき、Visual Studio でデバッグを続行できます。.ForEach バリアントを変更した後、ラムダ式が含まれているため、デバッグ セッションを再起動して再コンパイルする必要があります (VS 2008)

于 2010-02-09T16:21:37.163 に答える
0

これは本当に主観的な答えです:

.ForEach を好まないことの背後にある哲学的な理由には、あまり同意できません。コンピューター サイエンスのバックグラウンドがないせいかもしれませんが、わかりません。

私には、2 番目のコード セットの方が読みやすく、ごちゃごちゃしていないように見えます。他の人が述べたように、ToList() はちょっと残念ですが、それでも私には良く見えます。

Daniel Brückner のソリューションはさらに気に入っています。他の提案されたソリューションのいずれよりも優れているようです。

于 2010-02-09T16:20:24.110 に答える