【发布时间】:2014-12-14 22:21:22
【问题描述】:
我想编写一个函数,它接受一个列表并返回满足给定条件的所有可能子集的列表。 例如,我想拥有 [1,2,3,4] 的所有 3 尺寸子集,但没有任何包含 2 和 3 的子集。
$> func [1,2,3,4] 3
[[1,2,4],[1,3,4]]
要生成所有大小为 N 的子集,我有以下函数(找到 here):
kCombinations :: [a] -> Integer -> [[a]]
kCombinations _ 0 = [[]]
kCombinations [] _ = []
kCombinations (x:xs) k = withHead ++ withoutHead
where withHead = map (x:) (kCombinations xs (k-1))
withoutHead = kCombinations xs k
我知道我的问题最简单的解决方案是首先生成所有组合,然后使用过滤器功能。但是对于像kCombinations [1..30] 6 这样更大的问题,需要很长时间才能完成。
您能告诉我如何在生成所有组合的过程中过滤掉一些数据吗?
【问题讨论】:
-
您是在问如何在少于 O(2^n) 的时间内计算出 O(2^n) 的值吗?
-
您的病情如何?它是否允许仅基于其中的几个元素(如您的示例)排除某些子集?
-
30 choose 6是593775,所以我预计如果不只是打印出来(如果您正在打印列表),它需要一些时间。在 GHCi 中,我的计算机需要大约 2 秒来计算它,而打印它需要更长的时间(我没有等待它完成)。您可能可以使用差异列表对其进行一些改进,因为您经常追加,特别是因为它看起来很多都会与左侧相关联。
标签: algorithm haskell optimization complexity-theory