Reputation: 2096
So I was trying to write a simple recursive function to create permutations of a set. It creates an array of hash tables - each table being one permutation. I ran a quick test - worked!
Then, I stored the result in a variable, and now it doesn't work anymore. All the rows in the result variable are the same as the expected last row.
Why is the result different when stored in a variable? Is this a powershell bug due to some optimization?
function simple($data, $index)
{
if ($index -lt 0) {
$data.count = $global:count
$global:count = $global:count + 1
$data ### This is the return value
} else {
$name = "Name_$index"
$data.$name = $index + 100
simple $data ($index - 1)
$data.$name = $index + 200
simple $data ($index - 1)
}
}
# Case1: Just let the results print - works as expected
$global:count = 0
$d = [ordered]@{Count = -1; Name_0 = -1; Name_1 = -1}
Write-Output "Case 1: Show return value"
simple $d 1
# Case2: Just let the results print - works as expected
$global:count = 0
$d = [ordered]@{Count = -1; Name_0 = -1; Name_1 = -1}
Write-Output "Case 2: Store then show return value"
$a = simple $d 1
$a
The results are:
Case 1: Show return value
Name Value
---- -----
count 0
Name_0 100
Name_1 101
count 1
Name_0 200
Name_1 101
count 2
Name_0 100
Name_1 201
count 3
Name_0 200
Name_1 201
Case 2: Store then show return value
count 3
Name_0 200
Name_1 201
count 3
Name_0 200
Name_1 201
count 3
Name_0 200
Name_1 201
count 3
Name_0 200
Name_1 201
Upvotes: 2
Views: 179
Reputation: 5114
The issue lies in how the data is being sent out of the function. The same object is being outputted multiple times.
In the first example when you do not assign the output to a variable you are printing the data AS-IS as it comes out of the function. Every time you send $data out it prints as it is at the time $data is sent out of your function.
When you assign the output to a variable what is happening is you are outputting $data to the variable, but you do not see the values at that time so you don't see what they are right then. Then you are updating the value of that same object $data and outputting that again and storing again in variable, but they are the same object so now both the previous output and the new output are the same. This continues. When you output your $a variable which happen to be an array it outputs the same $data object as may times as it was stored with whatever values you last sent to it.
Hope that makes sense. Maybe this will help
function Test-HashUpdate {
param (
$hash
)
$hash.count++
Write-Output $hash
$hash.count++
Write-Output $hash
}
function Test-HashUpdateClone {
param (
$hash
)
$hash.count++
Write-Output $hash.Clone()
$hash.count++
Write-Output $hash.Clone()
}
$hash = @{count = 1 }
$a = test-HashUpdate $hash
$b = Test-HashUpdateClone $hash
Write-host "Hashtable outputted without clone"
$a
Write-host "`nHashtable outputted with clone"
$b
Output
Hashtable outputted without clone
Name Value
---- -----
count 5
count 5
Hashtable outputted with clone
count 4
count 5
Upvotes: 3