Powershell,内置了什么样的交集? [英] Powershell, kind of set intersection built-in?

查看:111
本文介绍了Powershell,内置了什么样的交集?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于某些需要从一堆松散的字母中找到字谜的游戏,我最终实现了一种置换算法,以找到所有可能的字谜,并过滤已知字母位置所需的那些字谜(顺便说一句,-match非常棒).但是对于较长的单词,这证明非常容易出错,因为浏览大量的胡言乱语并不能真正揭示隐藏在其中的正确单词.

For some game where one would need to find anagrams from a bunch of loose letters I ended up implementing a permutation algorithm to find all possible anagrams and filter those if needed for known letter positions (-match is great, by the way). But for longer words this proved very much error-prone, as skimming a large list of gibberish doesn't really reveal the proper words that were hidden within.

所以我认为 if 我会有一大堆英语单词(应该可以在某个地方获得),我可以将我的排列列表与适当的列表相交单词,并从排列列表中(希望)获得所有真实单词.

So I thought that if I would have a large list of English words (should be obtainable somewhere) I could just intersect my list of permutations with the list of proper words and get (hopefully) all real words from the permutation list.

由于PS中的许多运算符对集合的处理方式不同,所以我认为我可以做类似的事情

Since many operators in PS work differently with collections I thought I could just do something like

$wordlist -contains $permlist

并返回交点.不幸的是,这并不容易.我想到的其他选项是遍历一个列表并对每个项目执行-contains:

and get the intersection back. Unfortunately it's not that easy. Other options I have thought of would be to iterate over one list and do a -contains for each item:

$permlist | ? { $wordlist -contains $_ }

我认为这可能会起作用,但也非常慢(尤其是当$wordlistgc wordlist.txt的结果时).或者我可以构建一个巨大的正则表达式:

This probably would work but is also very slow, I think (especially when $wordlist is the result of a gc wordlist.txt). Or I could build a gigantic regular expression:

$wordlist -matches (($permlist | %{ "^$_`$" }) -join "|")

但是那也不可能很快.我也许也可以将findstr与上述巨大的正则表达式一起使用,但这感觉是错误的.

But that would probably not be very fast either. I could maybe also use findstr with above gigantic regex but that feels just wrong.

我是否可以使用任何内置的解决方案,这些解决方案比到目前为止的尝试要好?否则,我可能会将单词列表放入哈希表中,并使用迭代-contains方法,该方法应该足够快.

Are there any built-in solutions I could use and that are better than my attempts so far? Otherwise I'd probably put the word list into a hashtable and use the iterative -contains approach which should be fast enough then.

推荐答案

$left = New-HashSet string
$left.Add("foo")
$left.Add("bar")
$right = New-HashSet string
$right.Add("bar")
$right.Add("baz")

$left.IntersectWith($right)
$left.UnionWith($right)

(从 Josh Einstein 借用New-HashSet)

(borrowing New-HashSet from Josh Einstein)

警告:HashSet上的那些方法是就地算法,会修改原始集合.如果要对不可变的对象进行功能样式的转换,则需要将LINQ引入聚会:

Warning: those methods on HashSet are in-place algorithms that modify the original collection. If you want functional-style transform on immutable objects, you'll need to bring LINQ to the party:

add-type system.core

$asqueryable = [system.linq.queryable].getmethods() | ? { $_.name -eq "AsQueryable" } | select -first 1
$asqueryable = $asqueryable.MakeGenericMethod([string])
$leftAsQueryable = $asqueryable.Invoke($null, (,$left))

$intersect = [system.linq.queryable].getmethods() | ? { $_.name -eq "Intersect" } | select -first 1
$intersect = $intersect.MakeGenericMethod([string])
$result = $intersect.Invoke($null, ($leftAsQueryable, $right))

很显然,有人需要将此静态通用反射废话包装到友好的cmdlet中!不用担心,我正在努力...

Clearly, someone needs to wrap this static-generic-reflection crap into a friendly cmdlet! Don't worry, I'm working on it...

这篇关于Powershell,内置了什么样的交集?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆