Listコレクションに整数値のコレクションがあります。関数の引数の1つがコレクション値であるコレクション内の各値に対して関数を呼び出したい。 foreachループでこれを行わずに... lambda/linq式でこれを達成する方法はありますか?
次のような... myList.Where(p => myFunc(p.Value));
?
事前に感謝、-s
LINQはここでは役に立ちませんが、 List<T>.ForEach
を使用できます。
List <T> .ForEachメソッド
リストの各要素で指定されたアクションを実行します。
例:
myList.ForEach(p => myFunc(p));
ラムダ式に渡される値はリスト項目です。したがって、この例では、p
がList<long>
の場合、long
はmyList
です。
他のポスターが指摘したように、List<T>.ForEach
を使用できます。
ただし、任意のIEnumerable<T>
でForEachを使用できる拡張メソッドを簡単に作成できます。
public static void ForEach<T>(this IEnumerable<T> source, Action<T> action)
{
foreach(T item in source)
action(item);
}
つまり、次のことができるようになります。
myList.Where( ... ).ForEach( ... );
うん! List.ForEach
を使用できますが、問題はリストに対してのみ機能します(確実にすべてをオンザフライでリストに変更できますが、より少ないコードでもっと楽しく:) )。また、戻り値の型を提供しないAction<>
予測を使用する必要があります。
とにかくあなたが望んでいたものに対する答えがあります、あなたはFunc<>
で推測したのと同じ方法でそれを可能にすることができますが、以下のような小さなトリックで:
ここですべてをその場で行います:
string[] items = (new string[] { "d", "f" }).
Select(x => new Func<string>(() => {
//Do something here...
Console.WriteLine(x);
return x.ToUpper();
}
)).Select(t => t.Invoke()).ToArray<string>();
ここにはいくつかのポイントがあります。
最初に、LINQをサポートするコレクションで置き換えることができる文字列配列をその場で定義しました。
Second、Select
one Func<string>
の内部は、指定された配列の各要素に対して、呼び出されたときに宣言されますx
。
(空の括弧を見て、Func<type**1**, type**2**, ..., type**n**>
を定義するときは常に最後の型が戻り型であるため、単にFunc<string>
と書くと関数を示すことに注意してください入力パラメーターがなく、戻り値のタイプはstring)
与えられた配列(new string[] { "d", "f" })
に対して関数を使用したいのは明らかであり、それがパラメーターなしで関数を定義し、Func<>
内で同じ変数x
を使用した理由です。同じ配列要素を参照します。
Third、second Selectを配置しない場合、2つの関数のコレクションがあります。文字列を返し、すでに最初の配列から入力を取得しています。これを行い、結果をanonymous
変数に保持してから、それらの.Invoke
メソッドを呼び出すことができます。ここに書きます:
var functions = (new string[] { "d", "f" }).
Select(x => new Func<string>(() => {
//Do something here...
Console.WriteLine(x);
return x.ToUpper();
}));
string[] items = functions.Select(t => t.Invoke()).ToArray<string>();
最後に、結果を配列に変換しました!これで文字列配列ができました!
すみません、長くなります!!役に立つといいのですが。
List.ForEachメソッドを次のように使用できます。
myList.ForEach(p => myFunc(p));
いいえ-リスト内の各アイテムに対して関数を呼び出す場合、リスト内の各アイテムに対して関数を呼び出す必要があります。
ただし、次のように、コードの「ビジネスエンド」を読みやすくするために、IList<T>.ForEach()
メソッドを少しの構文糖として使用できます。
items.ForEach(item => DoSomething(item));
List<T>
のForEachメソッドを使用するのではなく、IEnumerable<T>
を使用する場合(「LINQ:ing」の場合によくあるように)、 MoreLINQ をお勧めします。 = Jon Skeet等により作成.
MoreLINQはForEachを提供し、Pipe(およびその他のメソッドの束)も提供します。これらは各要素に対してアクションを実行しますが、同じIEnumerable<T>
(voidと比較して)を返します。
ミニ(まだ完全な)例です。
public class Employee
{
public string EmployeeNumber { get; set; }
public DateTime? HireDate { get; set; }
}
public class EmployeeCollection : List<Employee>
{ }
private void RunTest()
{
EmployeeCollection empcoll = new EmployeeCollection();
empcoll.Add(new Employee() { EmployeeNumber = "1111", HireDate = DateTime.Now });
empcoll.Add(new Employee() { EmployeeNumber = "3333", HireDate = DateTime.Now });
empcoll.Add(new Employee() { EmployeeNumber = "2222", HireDate = null });
empcoll.Add(new Employee() { EmployeeNumber = "4444", HireDate = null });
//Here's the "money" line!
empcoll.Where(x => x.HireDate.HasValue == false).ToList().ForEach(item => ReportEmployeeWithMissingHireDate(item.EmployeeNumber));
}
private void ReportEmployeeWithMissingHireDate(string employeeNumber)
{
Console.WriteLine("We need to find a HireDate for '{0}'!", employeeNumber);
}