Garbage collection is a process that the .NET Framework (upon which the PowerShell runtime works) uses to manage memory. The garbage collection (for applications – services are handled a bit differently) process basically covers X steps:
- Identify objects that won’t be used
- Delete them from memory
- Compact the space to make room for new objects
The first step is the critical point for PowerShell users. You may have noticed how the memory used in a PowerShell session can steadily climb (or suddenly climb if you’re dealing with a large number of objects). I talked about that in this tip. The .NET garbage collector looks for objects that are still in use or could possibly be in use in the near future (this is a gross oversimplification - if you are really interested in a detailed explanation of how garbage collection works in the .NET Framework, check out this article.)
What this means to scripters who are running into memory pressure issues is that the garbage collector will not reclaim any objects you have actively referenced (meaning that you’ve assigned them to a variable) in your current or higher scope.
Since this can sound a bit convoluted let’s look at an example.
I read a large file to parse it and leave the contents of the original stored in a variable
PS> $MyLargeFile = Get-Content MyLargeFile.txt PS> Foreach ($line in $MyLargeFile) { DoSomething $line | Out-File NewUpdatedLargeFile.txt }
One of the problems with the above pattern is that the original file remains saved in memory and doesn’t get released unless you explicitly remove the reference, either by using Remove-Variable or Remove-Item or by changing what $MyLargeFile points to by assigning another value to it.
This isn’t VBScript where you have to set values to “Nothing”, but you should be aware of what larger object sets you are retaining in memory.