本质上,作为Powershell脚本的一部分,我需要实现广度优先搜索。因此,我需要队列,并且认为System.Collections.Queue与其他任何队列一样好。但是,当我从队列中取出一个对象时,Powershell不会跟踪我添加到该对象的所有属性。

这里发生了什么?我如何进入我的属性(property)?

此示例演示了该问题:

$object = new-object object
add-member -membertype noteproperty -name AnInteger -value 2 -inputobject $object
$queue = new-object system.collections.queue
$queue.enqueue($object)
$dequeued = $queue.dequeue()

# 1. True - both variables refer to the same object.
$object -eq $dequeued
# 2. True - using the original variable, can access the property.
$object.AnInteger -ne $null
# 3. False. Err, What?
$dequeued.AnInteger -ne $null

解决方案和更多问题

我发现了自己的错误:add-member修改了PSObject的一个实例,而不是Object。似乎它为我创建了一个在添加属性之前包装$object的代码。因此,我需要创建一个PSObject或将出队的结果转换为PSObject

我仍然不了解这里发生的一切。 add-member是否修改了$object以引用其创建的PSObject?如果不是,那么Powershell运行时如何知道$object实际上是PSObject$object.gettype().nameObject而非PSCustomObject

最佳答案

当您使用PsObject时,它可以工作。但是,我不知道为什么它不能在.NET对象上工作

$object = new-object PsObject -property @{AnInteger=2}
$queue = new-object system.collections.queue
$queue.enqueue($object)
$dequeued = $queue.dequeue()

$object.Aninteger -eq $dequeued.AnInteger # returns True

其他.NET集合显然也是如此:
$mynum  = 10 | add-member noteproperty MySecret 12345 -pass
$mynum.mysecret
$list = New-Object collections.arraylist
$list.Add($mynum)
$list[0].mysecret

$list[0] | fl * -force # shows nothing
$mynum | fl * -force   # shows mysecret

07-24 09:48
查看更多