L'ultizzo del ciclo
For Each...Next risulta molto interessante e di indubbia utilità, ma attenzione, potrebbe tranne in inganno.
Come riportato su
MSDN, "
...la proprietà Current dell'oggetto enumeratore è ReadOnly (Visual Basic) e restituisce una copia locale di ogni elemento dell'insieme. Pertanto non sarà possibile modificare gli elementi stessi in un ciclo For Each...Next. Le eventuali modifiche apportate influenzano solo la copia locale di Current e non si riflettono nell'insieme sottostante. Se tuttavia un elemento è un tipo di riferimento, sarà possibile modificare i membri dell'istanza a cui esso punta."
Supponiamo un ciclo molto banale, magari tra gli elementi di un array di stringhe.
Come nell'esempio riportato cicliamo tra gli elementi dell'array e tentiamo di modificare il valore. Dato che all'interno del ciclo lavoriamo con una copia dei vari elementi, l'elemento base non verrà modificato.
Private Sub mySyb
Dim myFld() As String = {"Pippo", "Pluto", "Paperino"}
For Each s As String In myFld
s = "Minnie"
Next
'
' Verifica del valore
'
Debug.Print(myFld(0))
Debug.Print(myFld(1))
Debug.Print(myFld(2))
End Sub
/* Ouptup
Pippo
Pluto
Paperino
*/
Identica cosa per quanto riguarda gli integer:
Private Sub mySyb
Dim myFld() As Integer = {1, 2, 3}
For Each i As Integer In myFld
i += 10
'
' Il valore qui è realmente variato, ma si tratta di una copia
'
Debug.Print(i)
Next
'
' Verifica del valore
'
Debug.Print(myFld(0))
Debug.Print(myFld(1))
Debug.Print(myFld(2))
End Sub
/* Ouptup
1
2
3
*/
Per poter modificare i valori degli elementi sarà necessario far riferimento all'elemento stesso; qui di seguito un paio di esempi.
Private Sub mySub()
'
' Utilizzo una variabile integer per identificare i vari elementi
'
Dim myFld() As Integer = {1, 2, 3}
For x As Integer = LBound(myFld) To UBound(myFld)
myFld(x) += 10
Next
End Sub
Sfruttando sempre il ciclo For Each...Next mi avvalgo della funzione Array.IndexOf per recuperare l'indice dell'elemento e valorizzarlo.
Private Sub mySub()
'
' Utilizzo la funzione Array.IndexOf per ottenere l'indice dell'elemento nell'array
'
Dim myFld() As Integer = {1, 2, 3}
For Each i As Integer In myFld
myFld(Array.IndexOf(myFld, i)) += 10
Next
End Sub
Come detto in precedenza il valore dell'elemento può variare se questo è passato per
riferimento, come nel seguente esempio:
Private Sub mySub()
'
' Aggiungo all'arrey tre oggetti label.
'
Dim myFld() As Control = {Me.Label1, Me.Label2, Me.Label3}
For Each lbl As Label In myFld
lbl.Text = "Minnie"
Next
End Sub