foreach で複数の変数を使用できますか
foreach (var item1 in collection1;var items2 in collection2)
{
}
データベースから 2 つのコレクションをフェッチし、両方を ComboBox に追加する必要があるため、これを実行したいと考えています。
foreach で複数の変数を使用できますか
foreach (var item1 in collection1;var items2 in collection2)
{
}
データベースから 2 つのコレクションをフェッチし、両方を ComboBox に追加する必要があるため、これを実行したいと考えています。
LINQ を使用して配列を結合し、結果を匿名型に入れ、結果のコレクションを反復処理します。
var col = collection1.Join(collection2, x => x, y => y, (x, y) => new { X = x, Y = y });
foreach (var entry in col) {
// entry.X, entry.Y
}
編集:
回答を投稿するとき、私はそれを想定しcollection1
、collection2
さまざまなタイプが含まれていました。両方に同じ型が含まれているか、共通の基本型を共有している場合は、別の方法があります。
重複を許可する場合:
collection1.Concat(collection2); // same type
collection1.select(x => (baseType)x).Concat(collection2.select(x => (baseType)x)); // shared base type
重複なし:
collection1.Union(collection2); // same type
collection1.select(x => (baseType)x).Union(collection2.select(x => (baseType)x)); // shared base type
フォーム フレームワーク 4.0 以降 Zip は元のソリューションを置き換えることができます。
collection1.Zip(collection2, (x, y) => new { X = x, Y = y });
利用可能なほとんどの LINQ 関数の概要については、 101 LINQ サンプルを参照してください。
LINQ を使用しない場合は、2 つの階層的な foreach ループ (反復回数を増やす) または 1 つの foreach ループを使用して中間型を作成し、2 つ目の foreach ループを使用して中間型のコレクションを反復処理するか、コレクション内の型が同じ場合はそれらをリストに追加します (AddRange)
次に、この新しいリストを繰り返し処理します。
多くの道が 1 つの目標に通じています。その 1 つを選択するのはあなた次第です。
コレクションを圧縮できます
foreach (var item in collection1.Zip(collection2, (a, b) => new { A = a, B = b }))
{
var a = item.A;
var b = item.B;
// ...
}
これは、要素が同じ位置で一致することを前提としています (たとえば、collection1 の最初の要素が、collection2 の最初の要素を結合します)。それは非常に効率的です。
いいえ、ループ内の foreach で複数の変数を使用することはできません。言語リファレンスを確認してください。各コレクションのアイテム数が異なる場合はどうなるでしょうか?
両方のコレクションを反復処理する場合は、ユニオンを使用してみてください。
foreach (var item1 in collection1.Union(collection2))
{
...
}
foreach は、コレクション内の個々のアイテムを列挙するために使用されます。いいえ、できません。次から次へと使う必要があります。使用する方が良いでしょう:
void myfunc()
{}
foreach(var item1 in collection1){myfunc();}
foreach(var item2 in collection2){myfunc();}
よりも
foreach(var item1 in collection1)
foreach(var item2 in collection2)
{
myfunc();
}
これは n*m 回実行されます。前の例は n+m 回だけ実行されます。
あなたのコメントから判断すると、あなたが本当にやろうとしていることは、2 つのコレクションのデカルト積を取得することではなくUNION
、2 つのセットの [SQL] を取得することだと思います。次の 2 つのオプションがあります。
Concat
2 つのコレクション:
foreach(var items in collection1.Concat(collection2)) {}
繰り返して派手なことをする必要がないと仮定して、両方を別々に追加するだけです(おそらく最良/最も単純です):
myComboBox.Items.AddRange(collection1);
myComboBox.Items.AddRange(collection2);
ただし、 [SQL pseudocode] の n*m デカルト積が必要なcollection1 CROSS JOIN collection2
場合は、ネストされた 2 つの foreach ステートメントを使用します。
foreach(var item1 in collection1)
foreach(var item2 in collection2)
{
}
または、LINQ で 2 つを結合し、結合されたコレクションを反復処理できます。
foreach(var items in (from i1 in collection1
from i2 in collection2
select Tuple.Create(i1, i2)))
{
}
あるコレクションのアイテムを他のコレクションの対応するアイテムとペアリングしますか?
foreach (var pair in col1.Zip(col2, (Item1, Item2) => new { Item1, Item2 })
{
//do something with pair.Item1 and pair.Item2
}
注: 最初のコレクションに 10 個のアイテムがあり、2 番目のコレクションに 8 個のアイテムがある場合、8 つのペアが得られます。最初のコレクションの最後の 2 つのアイテムは、2 番目のコレクションに一致するものがないため削除されます。より一般的には、反復回数は になりますMin(col1.Count(), col2.Count())
。
1 つのコレクションのすべてのアイテムを反復処理してから、2 番目のコレクションのすべてのアイテムを反復処理しますか?
foreach (var element in col1.Concat(col2))
{
//do something with element
}
注: 最初のコレクションに 10 個の要素があり、2 番目のコレクションに 8 個の要素がある場合、このループは 18 回実行されます。より一般的には、反復回数は になりますcol1.Count() + col2.Count()
。
あるコレクションの各アイテムを他のコレクションの各アイテムとペアリングしますか?
foreach (var item1 in col1)
foreach (var item2 in col2)
{
//do something with item1 and item2
}
注: これはデカルト積であるため、当然のことながら、反復回数はコレクションのサイズの積です。項目が 10 個と 8 個の場合、ループは 80 回実行されます。一貫性を保つために、それはcol1.Count() * col2.Count()
.