来自C#背景并且是一个完整的PowerShell新手,我试图基于两个列表/数组进行简单的过滤。
目标:根据列表'过滤器'过滤列表'toFilter'的元素,以便仅保留'toFilter'元素,这些元素至少匹配'filter'中列出的一种模式。
理想情况下,我想使用管道或Linq(而不是嵌套循环)实现这一点。
在C#中,我会这样做:
string[] filter = {"A", "B", "C"};
string[] toFilter = {"AA", "AB", "DD"};
var filtered = toFilter.Where(s1 => filter.Any(s2 => s1.Contains(s2))).ToList();
甚至更短,使用方法组:
var filtered = toFilter.Where(s1 => filter.Any(s1.Contains)).ToList();
预期结果:
AA AB
对于Powershell,我发现an article描述了C#中Linq的powershell等价物,但显然我无法掌握语法。
我带来了以下解决方案:
$filter = @("A", "B", "C")
$toFilter = @("AA", "AB", "DD")
$filtered = $toFilter | where {[Linq.Enumerable]::Any([string[]]$filter, [Func[string,bool]]{ $_ -match $args[0] })}
但它导致一个空列表。
使用这两个数组来获得预期结果的正确方法是什么?
编辑: 显然我的解决方案有效,但它不是纯粹的LINQ,所以一个问题仍然有效。
答案 0 :(得分:3)
您的示例失败的原因是$_
和$args[0]
在内部委托中引用相同的内容。
这里没有必要使用LINQ - 您可以使用嵌套的Where-Object
子句执行相同的操作:
$filter = @("A", "B", "C")
$toFilter = @("AA", "AB", "DD")
$filtered = $toFilter | Where-Object {
$item = $_
@($filter |Where-Object {$item.Contains($_)}).Count -gt 0
}
答案 1 :(得分:1)
桌面上的卡片这是我使用LINQ的第一天。这似乎是我想要使用的东西。我试图尽可能地嵌套LINQ语句,尝试仅使用LINQ获得正确的结果。
[Linq.Enumerable]::where(
$toFilter,
[System.Func[System.Object,bool]]{
param($filterItem)
[Linq.Enumerable]::Any(
$filter,
[Func[System.Object,bool]]{
param($singlefilter)
# write-host "$filterItem -match $singlefilter"
$filterItem -match $singlefilter}
)
}
)
Where
使用$toFilter
和Any
检查每个$filter
每个$toFilter
项目。
答案 2 :(得分:-2)
{{1}}