3

我无法找到一种有效的方法来从 Haskell 中的 9 个元素列表中挑选出 4 个元素的所有排列。做同样事情的python方式:

itertools.permutations(range(9+1),4)

在 Haskell 中执行此操作的一种不太有效的方法:

nub . (map (take 4)) . permutations $ [1..9]

我想找到类似的东西:

permutations 4 [1..9]
4

4 回答 4

5

这是我的解决方案:

import Control.Arrow

select :: [a] -> [(a, [a])]
select [] = []
select (x:xs) = (x, xs) : map (second (x:)) (select xs)

perms :: Int -> [a] -> [[a]]
perms 0 _  = [[]]
perms n xs = do
    (y, ys) <- select xs
    fmap (y:) (perms (n - 1) ys)

它非常懒惰,甚至适用于无限列表,尽管那里的输出不是很有用。我没有费心实施对角化或类似的东西。对于有限列表,这很好。

于 2012-08-01T20:06:22.493 回答
2
pick :: Int -> [a] -> [[a]]
pick 0 _ = [[]]
pick _ [] = []
pick n (x : xs) = map (x :) (pick (n - 1) xs) ++ pick n xs

perms :: Int -> [a] -> [[a]]
perms n l = pick n l >>= permutations
于 2012-08-02T09:25:53.900 回答
1
replicateM 4 [1..9]

我相信会为你做这件事。它在Control.Monad

于 2012-08-01T21:24:27.473 回答
0

这个怎么样

import Data.List (delete)

perms :: (Eq a) => Int -> [a] -> [[a]]
perms 0 _  = [[]]
perms _ [] = [[]]
perms n xs = [ (x:ys) | x <- xs, ys <- perms (n-1) (delete x xs) ]

基本上,它说,一个集合中 n 个元素的排列是,选择任何元素作为结果的第一个元素,然后其余元素是来自集合其余部分的 n-1 个元素的排列。加上一些基本情况。假设列表中的元素是唯一的。

于 2012-08-01T23:51:37.810 回答