重複の可能性:
vb.netでネストされたブレーク/終了
GOTO
ダブルForEachを終了する唯一の方法はありますか?
For Each city in cities
For Each person in city.People
If IsOK(person) GOTO Found_
Next person
Next city
Found_:
' ...
質問はVB.NETに関するものですが、C#についても疑問に思っています...
重複の可能性:
vb.netでネストされたブレーク/終了
GOTO
ダブルForEachを終了する唯一の方法はありますか?
For Each city in cities
For Each person in city.People
If IsOK(person) GOTO Found_
Next person
Next city
Found_:
' ...
質問はVB.NETに関するものですが、C#についても疑問に思っています...
別の機能に入れて
Private Function FindPerson(cities As List(of City)) As Person
For Each city in cities
For Each person in city.People
If IsOK(person) Return person
Next person
Next city
Return Nothing
End Function
と...
Private Function ContainsPerson(cities As List(of City)) As Bool
For Each city in cities
For Each person in city.People
If IsOK(person) Return True
Next person
Next city
Return False
End Function
編集: VB構文を修正
LINQを使用しないのはなぜですか?
C#:
// Or use SingleOrDefault(...) if there can ever only be one.
var person = Cities.SelectMany(city => city.People)
.FirstOrDefault(person => IsOK(person));
if (person != null)
{
...
}
VB.Net(私の最善の試み、私はそれにそれほど冗長ではありません):
// Or use SingleOrDefault(...) if there can ever only be one.
Dim person = Cities.SelectMany(Function(city) city.People)
.FirstOrDefault(Function(person) IsOK(person));
If person Not Nothing Then
...
End If
何かがあるかどうかを確認するだけの場合は、代わりに拡張メソッドをIsOK(person)
使用してください。Any(...)
C#:
var isOK = Cities.SelectMany(city => city.People)
.Any(person => IsOK(person));
VB.Net(私の最善の試み、私はそれにそれほど冗長ではありません):
Dim isOK = Cities.SelectMany(Function(city) city.People)
.Any(Function(person) IsOK(person));
ハインジがこの質問に答えたように:
残念ながら、exit two levels of for
ステートメントはありませんが、避けるべきいくつかの回避策がありますGoto
。これは悪い習慣と見なされます。
ダミーのアウターブロック
Do
For Each item In itemList
For Each item1 In itemList1
If item1.Text = "bla bla bla" Then
Exit Do
End If
Next
Next
Loop While False
また
Try
For Each item In itemlist
For Each item1 In itemlist1
If item1 = "bla bla bla" Then
Exit Try
End If
Next
Next
Finally
End Try
別の関数:ループを別の関数内に配置します。この関数は。で終了できますreturn
。ただし、ループ内で使用するローカル変数の数によっては、多くのパラメーターを渡す必要がある場合があります。別の方法は、ブロックを複数行のラムダに配置することです。これにより、ローカル変数がクロージャになります。
ブール変数:ネストされたループのレイヤー数によっては、コードが少し読みにくくなる可能性があります。
Dim done = False
For Each item In itemList
For Each item1 In itemList1
If item1.Text = "bla bla bla" Then
done = True
Exit For
End If
Next
If done Then Exit For
Next
最初のループにboolを入れ、内側のループでfalseに設定してから、中断することができます。次に、ブール値がfalseの場合、外側のループでブレークします。
例外をスローすることもできます。
Try
For Each city in cities
For Each person in city.People
If IsOK(person) Throw New FoundException
Next person
Next city
Catch ex As FoundException
DoFoundStuff
End Try
警告:私のポイントは、例外が複数のネストされたループを終了するためのオプションであることを示すことであり、このコード例の特定の場合には適切ではありません。特に、例外は通常、「通常の」状態ではなく「例外/エラー」状態に限定する必要があります。たとえば、単に「If」を「If Not IsOK ....」に変更した場合、例外が正しい解決策である可能性があります。
ブール値を追加し、人が見つかったときにtrueに設定して、内側のループから抜け出します。次に、見つかったものが真であるかどうかを確認します。もしそうなら、外側のループから抜け出します。
bool found;
For Each city in cities
For Each person in city.People
If IsOK(person)
found = true
Exit For
End If
Next person
If (found)
Exit For
End If
Next city
vb.netを書くのは何年も前のことですが、次のことがうまくいくはずです(私は考えています)
Dim found As Boolean
For Each city In cities
If found = True Then
Exit For
End If
For Each person In city.People
If IsOK(person) Then
found = True
Exit For
End If
Next person
Next city
888の答えに加えて:追加の関数は必ずしもパラメータを渡す必要はありません:
Dim a, b, c As Integer
a = 100
b = 50
c = 20
Dim r = Function()
For i = 1 To a
For j = 1 To b
For k = 1 To c
If i * j * k = 150 Then Return 1
Next
Next
Next
Return 2
End Function
Console.WriteLine(r)
キーワード:閉鎖