方法调用失败,因为 [System.Collections.ObjectModel.Collection`1[[]] 不包含我添加到 pscustomobject 的方法
Method invocation failed because [System.Collections.ObjectModel.Collection`1[[]] does not contain a method which I added to pscustomobject
我们有一个 json 文件,其中包含一个数组,其中包含带有销售价格的产品以及一些(我们必须购买的产品)零件号和购买价格。例如:
{
"Prices":[
{
"Product":"AD User",
"Price":3.52
},
{
"Product":"Skype for Business Plus SAL",
"Price":4.68,
"Part number":"6SH-00002",
"Buy price":3.90
},
{
"Product":"Citrix CAL",
"Price":6.40,
"Part number":"ROYSPLACXABASE",
"Buy price":5.33
}
]
}
我使用以下代码检索 json 的内容,对于每个具有部件号的对象,我将一个对象放入 PSCustomObjects 数组,并添加一个 int OrderCount 和一个函数来递增此 OrderCount :
$PurchaseOrder = @()
[object[]]$Prices = Get-Content 'C:\Pricelist.json' | Out-String | ConvertFrom-Json
foreach($_price in ($Prices.prices | Where-Object {$_."Part Number"})){
$PurchaseOrderItem = $_price.psobject.copy()
$PurchaseOrderItem | Add-Member -Name "OrderCount" -MemberType NoteProperty -Value 0
$PurchaseOrderItem | Add-Member -MemberType ScriptMethod -Name IncrementOrderCount {
param([int]$amount)
$this.OrderCount = $this.OrderCount + $amount
}
$PurchaseOrder += $PurchaseOrderItem
}
如果想出以下函数来更新 $PurchaseOrder:
function Update-PurchaseOrder{
[Cmdletbinding()]
param(
[ref]$PurchaseOrder,
[string]$ProductName,
[int]$Count
)
$PurchaseOrder.Value.where({$_.Product -eq $ProductName}).IncrementOrderCount($Count)
}
相反,当我 运行 这个函数
时,我得到以下错误
Update-PurchaseOrder -PurchaseOrder ([ref]$PurchaseOrder) -ProductName "Citrix CAL" -Count 5
Method invocation failed because [System.Collections.ObjectModel.Collection`1[[System.Management.Automation.PSObject, System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35]]] does not contain a
method named 'IncrementOrderCount'.
At line:9 char:5
+ $PurchaseOrder.Value.where({$_.Name -eq $ProductName}).IncrementO ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : MethodNotFound
如果我 运行 此代码带有手动创建的 $Prices
对象,例如:
$Prices = @([pscustomobject]@{Product="Product1";Price=1},[pscustomobject]@{Product="Product2";Price=2})
运行 没有任何问题。我试图将几个对象转换为不同的类型,但我别无选择。
我添加了一段额外的代码来检查我的采购订单中是否存在该产品,现在 运行 没问题了。
Write-Verbose "Updating PurchaseOrder for product $Title "
if($PurchaseOrder.Value.where({$_.Product -eq $Title})){
try{
$PurchaseOrder.Value.where({$_.Product -eq $Title}).IncrementOrderCount($Count)
} catch {
Write-Warning "Error while incrementing OrderCount for product $($Title): $($_.Exception.Message)"
}
} else {
Write-Verbose "Product $Title not found in PurchaseOrder."
}
使用ForEach-Object
遍历集合,然后对每个对象调用该方法。
另外 属性 的产品名称是 Product
而不是名称。
function Update-PurchaseOrder{
[Cmdletbinding()]
param(
[ref]$PurchaseOrder,
[string]$ProductName,
[int]$Count
)
$PurchaseOrder.Value.where({$_.Product -eq $ProductName}) | ForEach-Object {$_.IncrementOrderCount($Count)}
}
此外,我相信 $PurchaseOrder
已经通过引用传递,因此您可以跳过额外的麻烦,只需传递 $PurchaseOrder
而不是 ([ref]$PurchaseOrder)
。然后不需要在函数中解包值的额外步骤。
我们有一个 json 文件,其中包含一个数组,其中包含带有销售价格的产品以及一些(我们必须购买的产品)零件号和购买价格。例如:
{
"Prices":[
{
"Product":"AD User",
"Price":3.52
},
{
"Product":"Skype for Business Plus SAL",
"Price":4.68,
"Part number":"6SH-00002",
"Buy price":3.90
},
{
"Product":"Citrix CAL",
"Price":6.40,
"Part number":"ROYSPLACXABASE",
"Buy price":5.33
}
]
}
我使用以下代码检索 json 的内容,对于每个具有部件号的对象,我将一个对象放入 PSCustomObjects 数组,并添加一个 int OrderCount 和一个函数来递增此 OrderCount :
$PurchaseOrder = @()
[object[]]$Prices = Get-Content 'C:\Pricelist.json' | Out-String | ConvertFrom-Json
foreach($_price in ($Prices.prices | Where-Object {$_."Part Number"})){
$PurchaseOrderItem = $_price.psobject.copy()
$PurchaseOrderItem | Add-Member -Name "OrderCount" -MemberType NoteProperty -Value 0
$PurchaseOrderItem | Add-Member -MemberType ScriptMethod -Name IncrementOrderCount {
param([int]$amount)
$this.OrderCount = $this.OrderCount + $amount
}
$PurchaseOrder += $PurchaseOrderItem
}
如果想出以下函数来更新 $PurchaseOrder:
function Update-PurchaseOrder{
[Cmdletbinding()]
param(
[ref]$PurchaseOrder,
[string]$ProductName,
[int]$Count
)
$PurchaseOrder.Value.where({$_.Product -eq $ProductName}).IncrementOrderCount($Count)
}
相反,当我 运行 这个函数
时,我得到以下错误Update-PurchaseOrder -PurchaseOrder ([ref]$PurchaseOrder) -ProductName "Citrix CAL" -Count 5
Method invocation failed because [System.Collections.ObjectModel.Collection`1[[System.Management.Automation.PSObject, System.Management.Automation, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35]]] does not contain a
method named 'IncrementOrderCount'.
At line:9 char:5
+ $PurchaseOrder.Value.where({$_.Name -eq $ProductName}).IncrementO ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : MethodNotFound
如果我 运行 此代码带有手动创建的 $Prices
对象,例如:
$Prices = @([pscustomobject]@{Product="Product1";Price=1},[pscustomobject]@{Product="Product2";Price=2})
运行 没有任何问题。我试图将几个对象转换为不同的类型,但我别无选择。
我添加了一段额外的代码来检查我的采购订单中是否存在该产品,现在 运行 没问题了。
Write-Verbose "Updating PurchaseOrder for product $Title "
if($PurchaseOrder.Value.where({$_.Product -eq $Title})){
try{
$PurchaseOrder.Value.where({$_.Product -eq $Title}).IncrementOrderCount($Count)
} catch {
Write-Warning "Error while incrementing OrderCount for product $($Title): $($_.Exception.Message)"
}
} else {
Write-Verbose "Product $Title not found in PurchaseOrder."
}
使用ForEach-Object
遍历集合,然后对每个对象调用该方法。
另外 属性 的产品名称是 Product
而不是名称。
function Update-PurchaseOrder{
[Cmdletbinding()]
param(
[ref]$PurchaseOrder,
[string]$ProductName,
[int]$Count
)
$PurchaseOrder.Value.where({$_.Product -eq $ProductName}) | ForEach-Object {$_.IncrementOrderCount($Count)}
}
此外,我相信 $PurchaseOrder
已经通过引用传递,因此您可以跳过额外的麻烦,只需传递 $PurchaseOrder
而不是 ([ref]$PurchaseOrder)
。然后不需要在函数中解包值的额外步骤。