Credit: Mark Kraus Website: https://get-powershellblog.blogspot.com # Collection Type Guidence ## When to use what * Use Arrays if you know the element types and have a fixed length and/or known-up-front collection size that will not change. * Use ArrayList if you have an unkown collection size with either unknown or mixed type elements. * Use a Generic List when know the type of the elements but not the size of the collection. * Use a HashTable if you are going to do key based lookups on a collection and don't know the object type of the elements. * Use a Dictionary you are going to do key based lookups on a collection and you know the type of the elements. * Use a HashSet when you know the type of elements and just want unique values and quick lookups and assignmnets. * Use LinkList if you are going to make large numbers of additions and subtractions to an ordered list (and have the understanding to use this type) * Use Queue if you will build a collection that will need to be worked on First-in-first-out FIFO * Use Stack if you will build a collection that will need to be worked Last-in-first-out LIFO * Use SortedSet when you need a HasSet like set, but sorted (alaphbetically, for example) * Use SortedList when you need a List, but sorted (alaphbetically, for example) * Use SortedDictionary when you need a Dictionary, but sorted (alaphbetically, for example) ## Avoid the following: * Do not use Object[] * Do not use += on Arrays. If your collection will grow or shrink, use ArrayList or List * Do not use List for value types (int32, int64, char, etc) * avoid using Arrays, Lists, and ArrayLists for lookup/search operations, use ditcionaries and sets instead * Linked lists should only be considered in rediculously high volume add/remove operations to a list as the code complexity is too much for PowerShell * Only use "sorted" types when you really need to. If you only need it for reconstituion, sorting the keys and then foreaching them can work on small collections ## Examples ### Arrays https://docs.microsoft.com/en-us/dotnet/api/system.array?view=netframework-4.7.1 string array: ```powershell $Array = [string[]]@('string1','string2') ``` Int array: ```powershell $Array = [int[]]@(1,2,3,4,5) ``` ### ArrayList https://docs.microsoft.com/en-us/dotnet/api/system.collections.arraylist?view=netframework-4.7.1 ```powershell $ArrayList = [System.Collections.ArrayList]::new() $null = $ArrayList.Add(1) $null = $ArrayList.Add('String1') ``` ### List https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic.list-1?view=netframework-4.7.1 String: ```powershell $List = [System.Collections.Generic.List[String]]::new() $List.Add('String1') $List.Add('String2') ``` Int: ```powershell $List = [System.Collections.Generic.List[Int]]::new() $List.Add(1) $List.Add(2) ``` ### Hashtable https://docs.microsoft.com/en-us/dotnet/api/system.collections.hashtable?view=netframework-4.7.1 ```powershell $HashTable = @{ Key1 = "Value1" Key2 = "Value2" } ``` ### Dictionary https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic.dictionary-2?view=netframework-4.7.1 Case Sensitive (default) ```powershell $Dictionary = [System.Collections.Generic.Dictionary[String,String]]::New() $Dictionary['key1'] = 'Value1' $Dictionary['key2'] = 'Value2' # Is case sensitiveby default: $Dictionary['Key2'] = 'Value3' ``` Case Insensitive: ```powershell $Comparer = [System.StringComparer]::InvariantCultureIgnoreCase $Dictionary = [System.Collections.Generic.Dictionary[String,String]]::New($Comparer) $Dictionary['key1'] = 'Value1' $Dictionary['key2'] = 'Value2' # Will repllace the key above $Dictionary['Key2'] = 'Value3' ``` Example using processes and looking them up by PID: ```powershell $ProcessDict = [System.Collections.Generic.Dictionary[int,System.Diagnostics.Process]]::new() Get-Process | ForEach-Object { $ProcessDict[$_.Id] = $_ } $ProcessDict[0] | format-list * ```