about_Break

简短说明

介绍可用于立即退出 foreach、、forwhiledoswitchtrap 语句的语句。

长说明

语句 break 提供了一种退出当前控制块的方法。 在控制块后的下一个语句处继续执行。 语句支持标签。 标签是分配给脚本中的语句的名称。

break 循环中使用

break当语句出现在循环(如 foreachfordowhile 循环)中时,PowerShell 会立即退出循环。

break语句可以包含允许退出嵌入循环的标签。 标签可以指定脚本中的任何循环关键字 (keyword) ,例如 foreachforwhile

以下示例演示如何使用 break 语句退出 for 语句:

for($i=1; $i -le 10; $i++) {
   Write-Host $i
   break
}

在此示例中,break当变量等于 1 时, 语句退出for$i循环。 即使 语句的 for 计算结果为 True ,直到 $i 大于 10,PowerShell 在首次运行循环时 for 会到达 break 语句。

在必须满足内部条件的循环中使用 语句更为常见 break 。 请考虑以下 foreach 语句示例:

$i=0
$varB = 10,20,30,40
foreach ($val in $varB) {
  if ($val -eq 30) {
    break
  }
  $i++
}
Write-Host "30 was found in array index $i"

在此示例中, foreach 语句循环访问 $varB 数组。 在 if 运行循环的前两次且变量 $i 递增 1 时,语句的计算结果为 False。 第三次运行循环时, $i 等于 2, $val 变量等于 30。 此时,语句运行 breakforeach 循环退出。

在循环中使用标记 break

语句 break 可以包含标签。 如果将break关键字 (keyword) 与标签一起使用,PowerShell 会退出标记的循环,而不是退出当前循环。 标签是一个冒号,后跟你分配的名称。 标签必须是语句中的第一个标记,并且它必须后跟循环关键字 (keyword) ,例如 while

break 将执行移出标记的循环。 在嵌入式循环中,其结果与break关键字 (keyword) 单独使用时的结果不同。 此示例包含语句 while 的 语句 for

:myLabel while (<condition 1>) {
  for ($item in $items) {
    if (<condition 2>) {
      break myLabel
    }
    $item = $x   # A statement inside the For-loop
  }
}
$a = $c  # A statement after the labeled While-loop

如果条件 2 的计算结果为 True,则脚本的执行将跳到标记循环后的 语句。 在此示例中,使用 语句 $a = $c再次开始执行。

可以嵌套多个标记的循环,如以下示例所示。

:red while (<condition1>) {
  :yellow while (<condition2>) {
    while (<condition3>) {
      if ($a) {break}
      if ($b) {break red}
      if ($c) {break yellow}
    }
    Write-Host "After innermost loop"
  }
  Write-Host "After yellow loop"
}
Write-Host "After red loop"

如果变量 $b 的计算结果为 True,则脚本的执行将在标记为“red”的循环之后继续执行。 如果变量 $c 的计算结果为 True,则脚本控件在标记为“黄色”的循环之后继续执行。

如果变量 $a 的计算结果为 True,则执行将在最内部的循环之后恢复。 不需要标签。

PowerShell 不限制标签可以恢复执行的时间。 标签甚至可以跨脚本和函数调用边界传递控制。

break在语句中使用switch

在 构造中 switchbreak 使 PowerShell 退出 switch 代码块。

关键字 (keyword) break 用于离开 switch 构造。 例如,以下 switch 语句使用 break 语句来测试最具体的条件:

$var = "word2"
switch -regex ($var) {
    "word2" {
      Write-Host "Exact" $_
      break
    }

    "word.*" {
      Write-Host "Match on the prefix" $_
      break
    }

    "w.*" {
      Write-Host "Match on at least the first letter" $_
      break
    }

    default {
      Write-Host "No match" $_
      break
    }
}

在此示例中,将 $var 创建变量并将其初始化为 字符串值 word2。 语句 switch 使用 Regex 类首先将变量值与术语 word2匹配。 由于变量值与 语句中的 switch 第一个测试匹配,因此语句中的 switch 第一个代码块将运行。

当 PowerShell 到达第一个 break 语句时,语句 switch 将退出。 如果从示例中删除了四 break 个语句,则满足所有四个条件。 此示例使用 break 语句在满足最具体的条件时显示结果。

break在语句中使用trap

如果在语句正文中执行的最后一条 trap 语句是 break,则会禁止显示错误对象,并重新引发异常。

以下示例创建使用 trap 语句捕获的 DivideByZeroException 异常。

function test {
  trap [DivideByZeroException] {
    Write-Host 'divide by zero trapped'
    break
  }

  $i = 3
  'Before loop'
  while ($true) {
     "1 / $i = " + (1 / $i--)
  }
  'After loop'
}
test

请注意,执行在异常时停止。 After loop永远不会到达 。 异常在执行 后 trap 会重新引发。

Before loop
1 / 3 = 0.333333333333333
1 / 2 = 0.5
1 / 1 = 1
divide by zero trapped
ParentContainsErrorRecordException:
Line |
  10 |       "1 / $i = " + (1 / $i--)
     |       ~~~~~~~~~~~~~~~~~~~~~~~~
     | Attempted to divide by zero.

不要在循环switch外部使用 break 、 或trap

break 在直接支持它的构造外部使用 时, (循环、 switchtrap) ,PowerShell 会查找封闭构造的调用堆栈。 如果找不到封闭构造,则当前运行空间将静默终止。

这意味着,在支持它的封闭构造外部无意中使用 break 的函数和脚本可能会无意中终止其 调用方

break 管道 break(如脚本块) ForEach-Object 中使用 不仅会退出管道,还可能会终止整个运行空间。

另请参阅