Arrays explained

Hi Everyone,

I have been messing with powershell on and off for about a year now and I am having issues fully understanding arrays(if I have even used the correct term), for example when I save information to say $array that has a couple of columns or commas or headings etc and I try to use the array it does not always seem in the correct format. At the moment I am aware of about three different layouts and would like to know more and also how to convert from one to another and what is best when using for example the foreach statement. This has probably been explained in a previous post and if it has please point me in the correct direction.

Thanks

Check out this AMAZING article by MVP Kevin Marquette

https://powershellexplained.com/2018-10-15-Powershell-arrays-Everything-you-wanted-to-know/

It would be easier if you could give a simple example in code. It sounds like you’re talking about objects too.

 

Like James says, Kevin Marquette’s posts are amazing.
However, I can understand that for a beginner they can be overvhelming.

First of all, are you making the difference between an array and a hashtable?
This wasn’t obvious for me at the beginning, and that’s why I ask…

Array elements are only values, separated by comas and declared between parenthesizes @(,)
Hasthables are Name/Value pairs, separated by semi-colons and declared between braces @{;}

The output of both methods below is Square

$Array = @('Square', 'Blue', '5')
$Array[0]
$HashTable = @{Shape = 'Square'; Color = 'Blue'; Weight = 5}
$HashTable.Shape

Now what’s your next question?

Also, just to go a bit further into Luc’s post above, a PSObject is an array of hashtables

#Create an empty array
$psobject = @()
#Add a hashtable to the array with [pscustomobject] accelerator
$psobject += [pscustomobject]@{Shape = 'Square'; Color = 'Blue'; Weight = 5}
#Add a hashtable to the array with New-Object
$psobject += New-Object -TypeName PSObject -Property @{Shape = 'Circle'; Color = 'Red'; Weight = 10}

$psobject

Output:

Shape  Color Weight
-----  ----- ------
Square Blue       5
Circle Red       10

I have just read and studied Mr Kevin Marquette’s article on arrays. Brilliantly written, very educational for beginners and learners. Many thanks to all of you who continue to share your knowledge and technical tips.

That’s… not quite correct, although I can understand the confusion from how PS plays fast and loose with the easy conversions!

Although both methods of creating a PSObject have the same result, and both are created with hashtables, neither are in any way a hashtable after the PSObject is created, and they were never each a hashtable array. The hashtable’s key/value pairs are pulled apart and converted into PSPropertyInfo objects in the PSObject’s internal `Properties` collection.

You can examine this in a few ways, but here is one:

$Object = [PSCustomObject]@{ Property1 = 10; Property2 = 15}
#Check out the properties directly; the true PSObject is hidden in PS as a secret '.PSObject' property of the stored object
$PropertyCollection = $Object.PSObject.Properties
# You probably won't guess what this actually is unless you already know ;)
$PropertyCollection.GetType() 
# Each single "property" is actually a discrete object of its own, with its own metadata properties
$PropertyCollection

An important distinction should be made, however – all objects that you can work with in PowerShell are actually PSObjects, because everything you can interact with in PowerShell always come wrapped in a PSObject wrapper. It’s essentially a universal interface for all objects in PowerShell which enables the Extended Type System to add arbitrary properties and methods via Add-Member and other internal methods beyond what the .NET object types normally have.

For example, in .NET languages like C#, not all objects have a `Count` property (this is typically restricted to collection-type objects like arrays, dictionaries, and Lists). However, in PowerShell, the ETS adds a property named `Count` to every object (this was added somewhere between v3 and v5 of PowerShell, to my memory) in part to make it easier to work with PS’s array-unwrapping behaviour that can otherwise be a little annoying to work with at times.

PSObjects created with New-Object or with [PSCustomObject] are a bit different, though. They don’t have a base object, so they’re kind of an empty bag with whatever ETS properties you’ve elected to give them via the hashtable construction. They don’t retain the original hashtable in any way; in the above example you can see how all the key/value pairs from the hashtable are mapped to properties in the internal collection, but the hashtable’s own properties (e.g., `$hashtable.Keys`) are completely gone and not retained anywhere.

It’s for this reason that such PSObjects are sometimes referred to as a “property bag”. :slight_smile:

 

Thanks for all the responses, I am still a bit confused so I will give examples that may help. When I sort my data into what I think are arrays they can turn out quite different for example sometimes the end up being separated by commas

eg

First name,Last name,age,id number

23451,fred,smith,21

9807,lisa,brown,19

and then other times they turn out in a really useful array like

eg

id number :23451

First name :fred

Last name :smith

age :21

id number :9807

First name :lisa

Last name :brown

age :19

Currently I would send the first one out to a temporary file and import it again to make it useful again, I would like to know the difference between the two and is there a way to convert it within powershell or is there something that I am not doing correctly for it to be this way in the first place. The code that produces the first example is below.

[pre]

$person = @()
$person += “First name,Last name,age,id number”

Foreach ($temp in $data)
{
If ($temp.‘id number’ -eq $new)
{

$person += $temp.‘id number’ + “,” + $temp.‘First name’ + “,” + $temp.‘Last name’ + “,” + $temp.age
}
Else
{
write-host $temp " NO"
}
}

[/pre]

Thanks for any help.