Powershell 如何搜索包含另一个数组中项目的对象数组?

Powershell 如何搜索包含另一个数组中项目的对象数组?,powershell,powershell-2.0,vmware,powercli,Powershell,Powershell 2.0,Vmware,Powercli,我有两个数组 包含虚拟机信息的对象数组,称为$vms,其中一个属性称为Name。类型如下: PowerCLI > $vms.GetType() IsPublic IsSerial Name BaseType -------- -------- ---- -------- True True Object[]

我有两个数组

包含虚拟机信息的对象数组,称为
$vms
,其中一个属性称为
Name
。类型如下:

PowerCLI > $vms.GetType()

IsPublic IsSerial Name                                     BaseType
-------- -------- ----                                     --------
True     True     Object[]                                 System.Array
我从名为
$importVMs
的CSV文件中导入了另一个数组,其中一个字段也称为
Name

如果
$vms
中不存在
$importVMs.Name
(即它不匹配任何
$vms.Name
),我想做一些工作。我想知道我是否可以通过管道来实现这一点,或者我必须迭代两个数组吗

如果(!$vms |?{$\u.Name-neq$importVms.Name){#work}

似乎无法使其工作。是否需要在
if
条件下
foreach
导入
$importVms

编辑

到目前为止,我的完整脚本:

Connect-VIServer -Server vCenter -Protocol https -Force | out-null
$importVms = Import-Csv vCenterVMs.csv
$VMHost = "esxi"
$currentVms = Get-VM
Write-Host "Current registered VMs" -ForeGroundColor Cyan
$currentVMs

Write-Host "Saved VMs to import" -ForeGroundColor Yellow
$importVms

$registered = @()
Write-Host "Importing VMs..." -ForeGroundColor White
#$importVms | ?{$_.Name -notcontains $currentVms}

foreach ($vm in $importVms) {
    if (! $currentVms.Name -contains $vm) {
        Write-Host "Importing $($vm.Name)"
        # put in a try block here
        $registeredVM = New-VM -VMFilePath $vm.VmPathName -VMHost $VMHost -Location $vm.Location
        $registeredList += $registeredVM.Name
    }
}

$registeredList
Disconnect-VIServer -Server * -Confirm:$false
vCenterVMs.csv看起来像

"Name","VmPathName","Location"
"test","[RAID5] test/test.vmx","testfolder"

使用to-notin或-notcontains运算符

$importvms | ?{$_.Name -notin $vms.name} | %{ Do Stuff }
别名
用于
Where
,而
%
用于
ForEach

好的,这不起作用。我们可以尝试从当前VM名称数组中构建一个正则表达式匹配字符串,并将每个导入的VM与之匹配,以查看它是否已经存在。尝试以下脚本:

Connect-VIServer -Server vCenter -Protocol https -Force | out-null
$importVms = Import-Csv vCenterVMs.csv
$VMHost = "esxi"
$currentVms = Get-VM
Write-Host "Current registered VMs" -ForeGroundColor Cyan
$currentVMs

Write-Host "Saved VMs to import" -ForeGroundColor Yellow
$importVms

$registered = @()
Write-Host "Importing VMs..." -ForeGroundColor White
#$importVms | ?{$_.Name -notcontains $currentVms}

$VMNameFilter = "($(($currentVms|%{[RegEx]::Escape($_.Name)}) -join "|"))"

foreach ($vm in $importVms) {
    if (! $vm.Name -match $VMNameFilter) {
        Write-Host "Importing $($vm.Name)"
        # put in a try block here
        $registeredVM = New-VM -VMFilePath $vm.VmPathName -VMHost $VMHost -Location $vm.Location
        $registeredList += $registeredVM.Name
    }
}

$registeredList
Disconnect-VIServer -Server * -Confirm:$false

另一种方式,最好在脚本中使用:

Foreach ($ImportVm in $ImportVms.name) { 
if ($vms.name -notcontains $ImportVm) {
DO STUFF }
}
Foreach循环遍历数组$ImportVMs中的VM名称,将$ImportVMs中的每个VM名称放在每个循环的变量$ImportVM中

然后,“if”语句检查$vms中的名称数组是否不包含当前循环中的$ImportVM。 如果此“If”语句的计算结果为true,则脚本将执行{}内的任何操作。
我只是把{做事}这里,因为你没有提到你想用这些虚拟机做什么。

Second Lal,这可能需要一些解释。它目前在自动低质量帖子队列中。我建议不要删除它,但你需要充实一下。我在我的答案中添加了一些解释。我在我的答案中添加了一些解释。没有那么多o解释一下,这只是一个基本的Foreach循环,里面有一个“If”语句。关于Powershell中Foreach的基本知识,我推荐这篇文章:If我使用
Foreach($ImportVm in$ImportVms.name)
则我无法访问
$ImportVm
的其他属性,例如执行脚本块中的
$ImportVm.VmPathName
。如果我使用
Foreach($ImportVm in$ImportVms)
If
条件始终匹配(不应该匹配时).Hi,我相信-notin是Powershell3+?我使用的是Powershell 2。此外,使用
-notcontains
总是在不应该的情况下产生正匹配。谢谢,我必须将
if
语句更改为
if($vm.Name-notmatch$VMNameFilter)
,以使其正常工作。