I've been wondering about the performance impact of functions in PowerShell. Let's say we want to generate 100.000 random numbers using System.Random.
$ranGen = New-Object System.Random
Executing
for ($i = 0; $i -lt 100000; $i++) {
$void = $ranGen.Next()
}
finishes within 0.19 seconds. I put the call inside a function
Get-RandomNumber {
param( $ranGen )
$ranGen.Next()
}
Executing
for ($i = 0; $i -lt 100000; $i++) {
$void = Get-RandomNumber $ranGen
}
takes about 4 seconds.
Why is there such a huge performance impact?
Is there a way I can use functions and still get the performance I have with the direct call?
Are there better (more performant) ways of code encapsulation in PowerShell?
a function call is expensive. The way to get around that is to put as much as you can IN the function. take a look at the following ...
$ranGen = New-Object System.Random
$RepeatCount = 1e4
'Basic for loop = {0}' -f (Measure-Command -Expression {
for ($i = 0; $i -lt $RepeatCount; $i++) {
$Null = $ranGen.Next()
}
}).TotalMilliseconds
'Core in function = {0}' -f (Measure-Command -Expression {
function Get-RandNum_Core {
param ($ranGen)
$ranGen.Next()
}
for ($i = 0; $i -lt $RepeatCount; $i++) {
$Null = Get-RandNum_Core $ranGen
}
}).TotalMilliseconds
'All in function = {0}' -f (Measure-Command -Expression {
function Get-RandNum_All {
param ($ranGen)
for ($i = 0; $i -lt $RepeatCount; $i++) {
$Null = $ranGen.Next()
}
}
Get-RandNum_All $ranGen
}).TotalMilliseconds
output ...
Basic for loop = 49.4918
Core in function = 701.5473
All in function = 19.5579
from what i vaguely recall [and can't find again], after a certain number of repeats, the function scriptblock gets JIT-ed ... that seems to be where the speed comes from.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With