For...Next 语句 (Visual Basic)

重复一组语句,直到循环计数器达到其最终值。

语法

For counter [ As datatype ] = start To end [ Step step ]
    [ statements ]
    [ Continue For ]
    [ statements ]
    [ Exit For ]
    [ statements ]
Next [ counter ]

部件

部件 DESCRIPTION
counter For 语句中是必需的。 数值变量。 用于循环的控制变量。 有关详细信息,请参阅本主题后面的“反驳论点”
datatype 可选。 counter 的数据类型。 有关详细信息,请参阅本主题后面的“反驳论点”
start 必填。 数值表达式。 counter 的初始值。
end 必填。 数值表达式。 counter 的最终值。
step 可选。 数值表达式。 每次通过循环递增 counter 的量。
statements 可选。 一个或多个语句在 ForNext 之间按照指定的次数运行。
Continue For 可选。 将控制权传输到下一循环迭代。
Exit For 可选。 将控制从 For 循环转移出去。
Next 必填。 终止For循环的定义。

注释

To 语句中使用关键字来指定计数器的范围。 您还可以在 Select...Case 语句 和数组声明中使用此关键字。 有关数组声明的信息,请参阅 Dim Statement

简单示例

当你想要重复一组语句若干次时,请使用 For...Next 结构。

在下面的示例中,index 变量以值 1 开始,并在循环的每次迭代中递增,直到 index 的值达到 5 后结束。

For index As Integer = 1 To 5
    Debug.Write(index.ToString & " ")
Next
Debug.WriteLine("")
' Output: 1 2 3 4 5

在下面的示例中,变量 `number` 从 2 开始,每次循环迭代减少 0.25,循环在 `number` 变为 0 时结束。 Step-.25 参数在循环每次迭代时将值减少 0.25。

For number As Double = 2 To 0 Step -0.25
    Debug.Write(number.ToString & " ")
Next
Debug.WriteLine("")
' Output: 2 1.75 1.5 1.25 1 0.75 0.5 0.25 0 

小窍门

当您事先不知道循环中语句运行的次数时,While...End While 语句Do...Loop 语句 是很好的选择。 但是,当你期望运行循环的特定次数时, For...Next 循环是更好的选择。 首次进入循环时,可以确定迭代数。

嵌套循环

可以通过将一个循环置于另一个循环中来嵌套 For 循环。 以下示例演示具有不同步骤值的嵌套ForNext结构。 外部循环为循环的每个迭代创建一个字符串。 内部循环中,在每次迭代时递减一个循环计数器变量。

For indexA = 1 To 3
    ' Create a new StringBuilder, which is used
    ' to efficiently build strings.
    Dim sb As New System.Text.StringBuilder()

    ' Append to the StringBuilder every third number
    ' from 20 to 1 descending.
    For indexB = 20 To 1 Step -3
        sb.Append(indexB.ToString)
        sb.Append(" ")
    Next indexB

    ' Display the line.
    Debug.WriteLine(sb.ToString)
Next indexA
' Output:
'  20 17 14 11 8 5 2
'  20 17 14 11 8 5 2
'  20 17 14 11 8 5 2

嵌套循环时,每个循环必须具有唯一的counter变量。

还可以相互嵌套不同类型的控件结构。 有关详细信息,请参阅 嵌套控件结构

退出并继续

语句 Exit For 会立即退出 For... Next 循环并立即将控制转移到 Next 语句后面的语句。

Continue For 语句将控制权立即传输到循环的下一次迭代。 有关详细信息,请参阅 Continue 语句

下面的示例说明了如何使用 Continue ForExit For 语句。

For index As Integer = 1 To 100000
    ' If index is between 5 and 7, continue
    ' with the next iteration.
    If index >= 5 AndAlso index <= 8 Then
        Continue For
    End If

    ' Display the index.
    Debug.Write(index.ToString & " ")

    ' If index is 10, exit the loop.
    If index = 10 Then
        Exit For
    End If
Next
Debug.WriteLine("")
' Output: 1 2 3 4 9 10

可以在Exit For中放置任意数量的For语句。 Next 循环。 在嵌套For 中使用 ... Next 循环,Exit For 退出最内部的循环,将控制转移到下一个更高级别的嵌套。

Exit For 通常在你评估某个条件(例如,在 If...Then...Else 结构中)之后使用。 你可能想要在以下情况中使用Exit For

  • 继续循环迭代是不必要的或不可能的。 错误值或终止请求可能会创建此条件。

  • A Try...Catch...Finally 语句用于捕获异常。 可以在Exit For块末尾使用Finally

  • 你有一个无休止的循环,这是一个循环,可以运行大量甚至无限次数。 如果检测到此类条件,可以使用 Exit For 来跳出循环。 有关详细信息,请参阅 Do...Loop 语句

技术实现

For...Next 循环启动时,Visual Basic 会依次计算 startendstep。 Visual Basic 在此时仅计算这些值,然后将其分配给 startcounter。 在语句块运行之前,Visual Basic 会将 counterend 进行比较。 如果 counter 已大于 end 值(或小于值,如果 step 为负值),则 For 循环结束,控制权将传递给紧跟在 Next 语句后面的语句。 否则,语句块将运行。

每次 Visual Basic 遇到Next语句时,它会将counter递增step然后返回For语句。 再一次,它将 counterend 进行比较,根据结果,要么运行代码块,要么退出循环。 此过程将继续执行,直到 counter 超过 end 或遇到 Exit For 语句。

循环直到counter已经超过end才会停止。 如果 counter 等于 end,循环将继续。 判断是否运行该块的比较为:当counter为正时,<end= step,当counter为负时,>end= step

如果在循环中更改值 counter ,则代码可能更难读取和调试。 更改值 startendstep 不会影响首次输入循环时确定的迭代值。

如果嵌套循环,则编译器在内部级别的 Next 语句之前遇到外部嵌套级别的 Next 语句时,会发出错误信号。 只有当在每个counter语句中指定Next时,编译器才能检测到此重叠错误。

Step 参数

值可以是正值或负值 step 。 此参数根据下表确定循环处理:

步骤值 如果条件为真,循环执行
正数或零 counter <= end
消极 counter >= end

默认值 step 为 1。

反驳论点

下表指示 counter 是否定义在整个 For…Next 循环中有效的新局部变量。 此决定取决于是否存在 datatype 以及 counter 是否已定义。

datatype 是否存在? counter 是否已定义? 结果(counter 是否定义了一个作用域覆盖整个 For...Next 循环的新局部变量)
是的 否,因为 counter 已定义。 如果 counter 的作用域不是局部的,将会发生编译时警告。
是的。 从表达式startendstep中推断数据类型。 有关类型推理的信息,请参阅 Option Infer 语句本地类型推理
是的 是的 是,但前提是现有 counter 变量在过程外部定义。 该变量保持独立。 如果现有 counter 变量的范围是过程本地的,则会发生编译时错误。
是的 是的。

确定迭代类型的数据类型 counter ,该类型必须是下列类型之一:

  • AByte、、SByteUShortShortUIntegerIntegerULongLong、、 DecimalSingleDouble

  • 使用Enum 语句声明的枚举。

  • 一个 Object

  • 具有以下运算符的类型 T ,其中 B 是可在表达式中使用的 Boolean 类型。

    Public Shared Operator >= (op1 As T, op2 As T) As B

    Public Shared Operator <= (op1 As T, op2 As T) As B

    Public Shared Operator - (op1 As T, op2 As T) As T

    Public Shared Operator + (op1 As T, op2 As T) As T

可以选择在counter语句中指定Next变量。 此语法可提高程序的可读性,尤其是在具有嵌套 For 循环的情况下。 必须指定出现在相应 For 语句中的变量。

startendstep 表达式的计算结果可以是扩大到类型 counter 的任何数据类型。 如果使用用户定义的类型counter,可能需要定义CType转换运算符,以便将类型startendstep转换为counter类型。

示例 1

以下示例从泛型列表中删除所有元素。 而不是 For Each...Next 语句, 示例显示按降序循环访问的 For...Next 语句。 该示例使用此技术, removeAt 因为该方法会导致移除的元素之后的元素具有较低的索引值。

Dim lst As New List(Of Integer) From {10, 20, 30, 40}

For index As Integer = lst.Count - 1 To 0 Step -1
    lst.RemoveAt(index)
Next

Debug.WriteLine(lst.Count.ToString)
' Output: 0

示例 2

下面的示例循环访问通过使用 Enum 语句声明的枚举。

Public Enum Mammals
    Buffalo
    Gazelle
    Mongoose
    Rhinoceros
    Whale
End Enum

Public Sub ListSomeMammals()
    For mammal As Mammals = Mammals.Gazelle To Mammals.Rhinoceros
        Debug.Write(mammal.ToString & " ")
    Next
    Debug.WriteLine("")
    ' Output: Gazelle Mongoose Rhinoceros
End Sub

示例 3

在以下示例中,语句参数使用一个类,该类对+->=<=运算符进行了重载。

Private Class Distance
    Public Property Number() As Double

    Public Sub New(ByVal number As Double)
        Me.Number = number
    End Sub

    ' Define operator overloads to support For...Next statements.
    Public Shared Operator +(ByVal op1 As Distance, ByVal op2 As Distance) As Distance
        Return New Distance(op1.Number + op2.Number)
    End Operator

    Public Shared Operator -(ByVal op1 As Distance, ByVal op2 As Distance) As Distance
        Return New Distance(op1.Number - op2.Number)
    End Operator

    Public Shared Operator >=(ByVal op1 As Distance, ByVal op2 As Distance) As Boolean
        Return (op1.Number >= op2.Number)
    End Operator

    Public Shared Operator <=(ByVal op1 As Distance, ByVal op2 As Distance) As Boolean
        Return (op1.Number <= op2.Number)
    End Operator
End Class

Public Sub ListDistances()
    Dim distFrom As New Distance(10)
    Dim distTo As New Distance(25)
    Dim distStep As New Distance(4)

    For dist As Distance = distFrom To distTo Step distStep
        Debug.Write(dist.Number.ToString & " ")
    Next
    Debug.WriteLine("")

    ' Output: 10 14 18 22 
End Sub

另请参阅