Powershell 如何合并数组以将数组中的一个值与所有值进行比较?
我不熟悉编写脚本,并且正在努力实现一些概念。我已经有了一个PowerShell脚本,它将接收用户的输入并将其存储到多个变量中。然后,它将查看一个.csv文件,并仅输出用户的多个输入与指定列中的值不同的行 例如,如果我有一个.csv文件,其中包含:Powershell 如何合并数组以将数组中的一个值与所有值进行比较?,powershell,Powershell,我不熟悉编写脚本,并且正在努力实现一些概念。我已经有了一个PowerShell脚本,它将接收用户的输入并将其存储到多个变量中。然后,它将查看一个.csv文件,并仅输出用户的多个输入与指定列中的值不同的行 例如,如果我有一个.csv文件,其中包含: value1, value2, value3 data1, data2, data3 data1, data2, data3 data1, data5, data3 data1, data2, data3 我要求输出value2与data5不同的行,
value1, value2, value3
data1, data2, data3
data1, data2, data3
data1, data5, data3
data1, data2, data3
我要求输出value2与data5不同的行,我得到以下输出:
value1, value2, value3
data1, data2, data3
data1, data2, data3
data1, data2, data3
以下是我目前使用的代码:
$path = Read-Host 'What is the file share path?'
$filteredvalue = Read-Host 'What value would you like to filter out?'
$filteredvalue2 = Read-Host 'What second value would you like to filter out?'
$filteredvalue3 = Read-Host 'What second value would you like to filter out?'
$filteredvalue4 = Read-Host 'What second value would you like to filter out?'
$filteredvalue5 = Read-Host 'What second value would you like to filter out?'
$filteredvalue6 = Read-Host 'What second value would you like to filter out?'
$filteredvalue7 = Read-Host 'What second value would you like to filter out?'
$file1 = $path
$filtered = Import-Csv -Path $file1 | where {$_.IdentityReference -notlike $filteredvalue -and $_.IdentityReference -notlike $filteredvalue2 -and $_.IdentityReference -notlike $filteredvalue3 -and $_.IdentityReference -notlike $filteredvalue4 -and $_.IdentityReference -notlike $filteredvalue5 -and $_.IdentityReference -notlike $filteredvalue6 -and $_.IdentityReference -notlike $filteredvalue7}
$file2 = "${path}_filtered.csv"
$filtered | Export-Csv -Path $file2 -NoTypeInformation
这是可行的,但不是最好的解决方案,因为我必须在代码中指定要过滤掉多少个值。我希望使用数组来避免为值创建所有变量
以下是我迄今为止尝试过但没有成功的方法:
$path = Read-Host 'What is the file share path?'
$Reponse = 'Y'
$filteredvalue = $Null
$filteredvalues = @()
Do
{
$filteredvalue = Read-Host 'What value would you like to filter out?'
$Response = Read-Host 'Would you like to filter out additional values? (y/n)'
$filteredvalues += $filteredvalue
}
Until ($Response -eq 'n')
$file1 = $path
$filtered = Import-Csv -Path $file1 | where {for($i = 0; $i -le $filteredvalues.GetUpperBound(0); $i++) {$_.IdentityReference -ne $filteredvalues[$i]}}
$file2 = "${path}_filtered.csv"
$filtered | Export-Csv -Path $file2 -NoTypeInformation
输出保持不变,没有任何内容被过滤掉。PowerShell提供-contains
,并且自v3起,也提供-in
——它们的区别仅在于输入数组是在LHS(-contains
)还是RHS(-in
)上
与PowerShell中的大多数运算符一样,它们也以否定形式存在,即-notcontains
和-notin
应用于您的代码:
$filtered = Import-Csv $file1 | Where-Object IdentityReference -notin $filteredValues
至于你所尝试的: 顺便说一下:使用
$filteredvalues.Count-1比使用$filteredvalues.GetUpperBound(0)
更容易
where
(where Object
)根据脚本块{…}
的输出是否计算为$true
,选择(通过)输入对象
您的for
-循环代码返回一个布尔数组,指示每个过滤器值的输入对象的.IdentityReference
是否与该值匹配
因此,使用2个或更多的过滤器值,您将得到一个至少包含1个$true
值的数组,并且任何这样的数组总的来说都会被解释为$true
例如:
PS> [bool] ($false, $true)
True
有关PowerShell如何将对象隐式计算为布尔值(到布尔值的转换)的概述,请参阅的下半部分
要使循环方法起作用,您必须在过滤器值匹配后立即将$false
作为标量返回,否则必须默认为$true
(注意使用foreach
更方便地枚举数组元素):
您应该使用-notin
操作符。语法是value-notin-array
请允许我向新来者提供标准建议:如果答案解决了您的问题,请单击大复选标记接受它(✓) 在它旁边,也可以选择向上投票(向上投票要求至少15个信誉点)。如果您发现其他答案有帮助,请向上投票。接受(您将获得2个信誉点)和向上投票有助于未来的读者。有关更多信息,请参阅。如果您的问题尚未完全回答,请提供反馈或
$filtered = Import-Csv -Path $file1 | where {
foreach ($filteredValue in $filteredValues) {
if ($_.IdentityReference -eq $filteredValue) { return $false }
}
return $true
}