Skip to content

Commit 629e8a9

Browse files
authored
Merge pull request #11563 from MicrosoftDocs/main
12/5/2024 PM Publish
2 parents e556093 + 4b8a740 commit 629e8a9

File tree

2 files changed

+159
-2
lines changed

2 files changed

+159
-2
lines changed

reference/docs-conceptual/dev-cross-plat/performance/script-authoring-considerations.md

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
---
22
description: Scripting for Performance in PowerShell
3-
ms.date: 05/07/2024
3+
ms.date: 12/05/2024
44
title: PowerShell scripting performance considerations
55
---
66

@@ -627,6 +627,67 @@ Unwrapped = 42.92 ms
627627
The unwrapped example is **372 times faster**. Also, notice that the first implementation requires
628628
the **Append** parameter, which isn't required for the later implementation.
629629

630+
## Object creation
631+
632+
Creating objects using the `New-Object` cmdlet can be slow. The following code compares the
633+
performance of creating objects using the `New-Object` cmdlet to the `[pscustomobject]` type
634+
accelerator.
635+
636+
```powershell
637+
Measure-Command {
638+
$test = 'PSCustomObject'
639+
for ($i = 0; $i -lt 100000; $i++) {
640+
$resultObject = [PSCustomObject]@{
641+
Name = 'Name'
642+
Path = 'FullName'
643+
}
644+
}
645+
} | Select-Object @{n='Test';e={$test}},TotalSeconds
646+
647+
Measure-Command {
648+
$test = 'New-Object'
649+
for ($i = 0; $i -lt 100000; $i++) {
650+
$resultObject = New-Object -TypeName PSObject -Property @{
651+
Name = 'Name'
652+
Path = 'FullName'
653+
}
654+
}
655+
} | Select-Object @{n='Test';e={$test}},TotalSeconds
656+
```
657+
658+
```Output
659+
Test TotalSeconds
660+
---- ------------
661+
PSCustomObject 0.48
662+
New-Object 3.37
663+
```
664+
665+
PowerShell 5.0 added the `new()` static method for all .NET types. The following code compares the
666+
performance of creating objects using the `New-Object` cmdlet to the `new()` method.
667+
668+
```powershell
669+
Measure-Command {
670+
$test = 'new() method'
671+
for ($i = 0; $i -lt 100000; $i++) {
672+
$sb = [System.Text.StringBuilder]::new(1000)
673+
}
674+
} | Select-Object @{n='Test';e={$test}},TotalSeconds
675+
676+
Measure-Command {
677+
$test = 'New-Object'
678+
for ($i = 0; $i -lt 100000; $i++) {
679+
$sb = New-Object -TypeName System.Text.StringBuilder -ArgumentList 1000
680+
}
681+
} | Select-Object @{n='Test';e={$test}},TotalSeconds
682+
```
683+
684+
```Output
685+
Test TotalSeconds
686+
---- ------------
687+
new() method 0.59
688+
New-Object 3.17
689+
```
690+
630691
## Use OrderedDictionary to dynamically create new objects
631692

632693
There are situations where we may need to dynamically create objects based on some input, the

reference/docs-conceptual/whats-new/What-s-New-in-PowerShell-75.md

Lines changed: 97 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
---
22
title: What's New in PowerShell 7.5
33
description: New features and changes released in PowerShell 7.5
4-
ms.date: 11/18/2024
4+
ms.date: 12/05/2024
55
---
66

77
# What's New in PowerShell 7.5
@@ -151,6 +151,102 @@ The following experimental features are included in PowerShell 7.5-rc.1:
151151
- [PSSerializeJSONLongEnumAsNumber][06] - `ConvertTo-Json` now treats large enums as numbers
152152
([#20999][20999]) (Thanks @jborean93!)
153153

154+
## Performance improvements
155+
156+
PowerShell 7.5-rc.1 included [PR#23901][23901] from @jborean93 that improves the performance of the
157+
`+=` operation for an array of objects.
158+
159+
The following example measures the performance for different methods of adding elements to an array.
160+
161+
```powershell
162+
$tests = @{
163+
'Direct Assignment' = {
164+
param($count)
165+
166+
$result = foreach($i in 1..$count) {
167+
$i
168+
}
169+
}
170+
'List<T>.Add(T)' = {
171+
param($count)
172+
173+
$result = [Collections.Generic.List[int]]::new()
174+
foreach($i in 1..$count) {
175+
$result.Add($i)
176+
}
177+
}
178+
'Array+= Operator' = {
179+
param($count)
180+
181+
$result = @()
182+
foreach($i in 1..$count) {
183+
$result += $i
184+
}
185+
}
186+
}
187+
188+
5kb, 10kb | ForEach-Object {
189+
$groupResult = foreach($test in $tests.GetEnumerator()) {
190+
$ms = (Measure-Command { & $test.Value -Count $_ }).TotalMilliseconds
191+
192+
[pscustomobject]@{
193+
CollectionSize = $_
194+
Test = $test.Key
195+
TotalMilliseconds = [math]::Round($ms, 2)
196+
}
197+
198+
[GC]::Collect()
199+
[GC]::WaitForPendingFinalizers()
200+
}
201+
202+
$groupResult = $groupResult | Sort-Object TotalMilliseconds
203+
$groupResult | Select-Object *, @{
204+
Name = 'RelativeSpeed'
205+
Expression = {
206+
$relativeSpeed = $_.TotalMilliseconds / $groupResult[0].TotalMilliseconds
207+
$speed = [math]::Round($relativeSpeed, 2).ToString() + 'x'
208+
if ($speed -eq '1x') { $speed } else { $speed + ' slower' }
209+
}
210+
} | Format-Table -AutoSize
211+
}
212+
```
213+
214+
When you run the script in PowerShell 7.4.6, you see that using the `+=` operator is the slowest
215+
method.
216+
217+
```Output
218+
CollectionSize Test TotalMilliseconds RelativeSpeed
219+
-------------- ---- ----------------- -------------
220+
5120 Direct Assignment 4.17 1x
221+
5120 List<T>.Add(T) 90.79 21.77x slower
222+
5120 Array+= Operator 342.58 82.15x slower
223+
224+
225+
CollectionSize Test TotalMilliseconds RelativeSpeed
226+
-------------- ---- ----------------- -------------
227+
10240 Direct Assignment 0.64 1x
228+
10240 List<T>.Add(T) 184.10 287.66x slower
229+
10240 Array+= Operator 1668.13 2606.45x slower
230+
```
231+
232+
When you run the script in PowerShell 7.5-rc.1, you see that using the `+=` operator is much faster
233+
than PowerShell 7.4.6. Now, it's also faster than using the `List<T>.Add(T)` method.
234+
235+
```Output
236+
CollectionSize Test TotalMilliseconds RelativeSpeed
237+
-------------- ---- ----------------- -------------
238+
5120 Direct Assignment 4.71 1x
239+
5120 Array+= Operator 40.42 8.58x slower
240+
5120 List<T>.Add(T) 92.17 19.57x slower
241+
242+
243+
CollectionSize Test TotalMilliseconds RelativeSpeed
244+
-------------- ---- ----------------- -------------
245+
10240 Direct Assignment 1.76 1x
246+
10240 Array+= Operator 104.73 59.51x slower
247+
10240 List<T>.Add(T) 173.00 98.3x slower
248+
```
249+
154250
<!-- end of content -->
155251
<!-- reference links -->
156252
[chg]: https://github.com/PowerShell/PowerShell/blob/master/CHANGELOG/preview.md

0 commit comments

Comments
 (0)