Вы сказали это сами, ваше узкое место связано с командным файлом в вашем скрипте, а не с самим l oop. foreach
(в отличие от ForEach-Object
) уже является более быстрым механизмом foreach
l oop в PowerShell. Исследуйте свой пакетный файл , чтобы выяснить, почему для его завершения требуется 30 секунд, и оптимизируйте его, где сможете.
Использование заданий
Примечание: Start-Job
запустит задание под другим процессом. Если у вас PowerShell Core , вы можете использовать командлет Start-ThreadJob
вместо Start-Job
. Это запустит вашу работу как часть другого потока того же процесса вместо запуска другого процесса.
Если вы не можете оптимизировать пакетный скрипт или оптимизировать его под свои нужды, тогда вы можете рассмотреть используя Start-Job
, чтобы запустить задание для асинхронного выполнения, а затем проверить результат и получить любые выходные данные, используя Receive-Job
. Например:
# Master list of jobs you need to check the result of later
$jobs = New-Object System.Collections.Generic.List[System.Management.Automation.Job]
# Run your script for each row
foreach ($row in $Dataset.tables[0].rows)
{
$UserID=$row.value
$DeviceID=$row.value1
$EmailAddress=$row.email_address
# Use Start-Job here to kick off the script and store the job information
# for later retrieval.
# The $using: scope modifier allows you to make use of variables that were
# defined in the session calling Start-Job
$job = Start-Job -ScriptBlock { cmd.exe /c "`"${using:PSScriptRoot}`"\bin\Script.bat -c `" -Switch ${using:UserID}`" >> `"${using:PSScriptRoot}`"\${using:FileName3}_REST_${DateTime}.txt 2> nul"; }
# Add the execution to the $jobs list to check the result of later
# Casting to void here prevents the Add method from returning the object
# we've added.
[void]$jobs.Add($job)
}
# Wait for the jobs to be done
Write-Host 'Waiting for all jobs to complete...'
while( $jobs | Where-Object { $_.State -eq 'Running' } ){
Start-Sleep -s 10
}
# Retrieve the output of the jobs
foreach( $j in $jobs ) {
Receive-Job $j
}
Примечание. Поскольку вам необходимо выполнить этот сценарий ~ 1000 раз, вы можете рассмотреть возможность написания своей логики c, чтобы выполнить только определенное количество заданий в время. В приведенном выше примере запускаются все необходимые задания без указания количества, которое может выполняться одновременно.
Для получения дополнительной информации о заданиях и свойствах, которые вы можете проверить в запущенном / завершенном задании, проверьте ссылки ниже:
* В документации говорится, что область действия using
может быть объявлена только при работе с удаленными сеансами, но , похоже, работает нормально с Start-Job
, даже если работа местная.