19

我想在 Powershell 中使用后台作业。

如何在 ScriptBlock 定义时评估变量?

$v1 = "123"
$v2 = "asdf"

$sb = {
    Write-Host "Values are: $v1, $v2"
}

$job = Start-Job -ScriptBlock $sb

$job | Wait-Job | Receive-Job

$job | Remove-Job

我打印出 $v1 和 $v2 的空值。我怎样才能让它们在(传递给)脚本块中进行评估,然后再传递给后台作业?

4

4 回答 4

36

一种方法是使用 [scriptblock]::create 方法从使用局部变量的可扩展字符串创建脚本块:

$v1 = "123"
$v2 = "asdf"

$sb = [scriptblock]::Create("Write-Host 'Values are: $v1, $v2'")

$job = Start-Job -ScriptBlock $sb

另一种方法是在 InitializationScript 中设置变量:

$Init_Script = {
$v1 = "123"
$v2 = "asdf"
}

$sb = {
    Write-Host "Values are: $v1, $v2"
}

$job = Start-Job -InitializationScript $Init_Script -ScriptBlock $sb 

第三种选择是使用 -Argumentlist 参数:

$v1 = "123"
$v2 = "asdf"

$sb = {
    Write-Host "Values are: $($args[0]), $($args[1])"
}

$job = Start-Job  -ScriptBlock $sb -ArgumentList $v1,$v2
于 2013-11-07T11:50:05.050 回答
17

最简单的解决方案(需要 V3 或更高版本)如下所示:

$v1 = "123"
$v2 = "asdf"

$sb = {
     Write-Host "Values are: $using:v1, $using:v2"
}

$job = Start-Job -ScriptBlock $sb

您可以认为 $using 大致类似于显式 param() 块并传递 -ArgumentList,只有 PowerShell 会自动为您处理。

于 2013-11-07T20:38:43.117 回答
3

在脚本块中将值声明为参数,然后使用-ArgumentList

$v1 = "123"
$v2 = "asdf"

$sb = {
    param
    (
        $v1,
        $v2
    )
    Write-Host "Values are: $v1, $v2"
}

$job = Start-Job -ScriptBlock $sb -ArgumentList $v1, $v2

$job | Wait-Job | Receive-Job

$job | Remove-Job
于 2013-11-07T11:48:20.743 回答
2

我不在计算机上进行验证,但这应该可以:

$sb = {
    param($p1,$p2)
    Write-Host "Values are: $p1, $p2"
}

$job = Start-Job -ScriptBlock $sb -ArgumentList $v1,$v2

当我开始工作时,我会仔细检查一下。

于 2013-11-07T11:48:33.133 回答