Ответ Стива Таунсенда верен в теории, но не на практике, как указал @likwid. Мой исправленный код учитывает барьер контекста работы - по умолчанию ничто не преодолевает этот барьер! Таким образом, автоматическая $_переменная может использоваться в цикле, но не может использоваться непосредственно в блоке сценария, потому что она находится внутри отдельного контекста, созданного заданием.
Чтобы передать переменные из родительского контекста в дочерний контекст, используйте -ArgumentListпараметр on Start-Jobдля его отправки и используйте paramвнутри блока скрипта для его получения.
cls
# Send in two root directory names, one that exists and one that does not.
# Should then get a "True" and a "False" result out the end.
"temp", "foo" | %{
$ScriptBlock = {
# accept the loop variable across the job-context barrier
param($name)
# Show the loop variable has made it through!
Write-Host "[processing '$name' inside the job]"
# Execute a command
Test-Path "\$name"
# Just wait for a bit...
Start-Sleep 5
}
# Show the loop variable here is correct
Write-Host "processing $_..."
# pass the loop variable across the job-context barrier
Start-Job $ScriptBlock -ArgumentList $_
}
# Wait for all to complete
While (Get-Job -State "Running") { Start-Sleep 2 }
# Display output from all jobs
Get-Job | Receive-Job
# Cleanup
Remove-Job *
(Обычно мне нравится давать ссылку на документацию PowerShell в качестве подтверждающего доказательства, но, увы, мой поиск оказался бесплодным. Если вы случайно знаете, где задокументировано разделение контекста, оставьте здесь комментарий, чтобы сообщить мне!)
receive-job (wait-job ($a = start-job { "heyo!" })); remove-job $aили$a = start-job { "heyo!" }; wait-job $a; receive-job $a; remove-job $aТакже обратите внимание, что если вы позвонитеreceive-jobдо завершения задания, вы можете вообще ничего не получить.