Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Poor Performance in Foreach -Parallel #10450

Copy link
Copy link
@jhoneill

Description

@jhoneill
Issue body actions

It was reported here PowerShell/PowerShell-RFC#194 by @Ayanmullick
that

The below script runs faster without -parallel than with.

(Get-WinEvent -ListLog * -EA SilentlyContinue).Where({$PSItem.recordcount -ne '0'}).Logname|
                ForEach-Object -Parallel {Get-WinEvent -FilterHashtable @{logname = "$PSItem";Starttime ='8/24/2019 11:00:00';Endtime ='8/24/2019 11:09:00';Level=1,2,3} -EA SilentlyContinue }

It took 18 secs to finish with -parallel and only 5 without.

Thomas Lee put up this case where it was slower. https://twitter.com/doctordns/status/1164461929093566465

It is understood that parallelizing trivial code in will more overhead than the time saved

Using Start-Parallel from the PowerShell Gallery I ran this to ping every machine on my local subnet. 200 addresses are not used, so in sequence it would take 800-1000 seconds.

1..254 | Start-Parallel -Scriptblock {param ($P) ping "192.168.0.$p" -n 1 | where {$_ -match "ttl="}} -MaxThreads 300

it took 9 seconds

The new equivalent is
1..254 | foreach -Parallel {ping "192.168.0.$_" -n 1 | where {$_ -match "ttl="}} -ThrottleLimit 300

Which takes 31 seconds; I would expect broadly similar performance with the cmdlet slightly faster.

Using threadjob which ships with PS 6 and 7 I created this

$j = 1..254 | foreach {  
   $sb=[scriptblock]::Create("ping -n 1 192.168.0.$_ | where {`$_ -match 'TTL=' } ")                                    
    Start-ThreadJob -ScriptBlock $sb -ThrottleLimit 300 }
 while ($j.state -eq "running" -or $j.hasmoredata -eq $true) {
foreach ($finished in $j.where({$_.state -eq "completed"})){ receive-job -Id $finished.id; }                       } 

Which runs in 11 seconds.
The cmdlet should be doing something very similar to this but not taking 3 times as long

Metadata

Metadata

Assignees

Labels

Issue-Questionideally support can be provided via other mechanisms, but sometimes folks do open an issue to get aideally support can be provided via other mechanisms, but sometimes folks do open an issue to get aWG-Engine-Performancecore PowerShell engine, interpreter, and runtime performancecore PowerShell engine, interpreter, and runtime performance

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions

    Morty Proxy This is a proxified and sanitized view of the page, visit original site.