2015-02-11 104 views
3

我刚刚学习Haskell,我想创建一个“混洗”函数,将两个列表混合在一起,交替出现,直到一个列表用完。因此,shuffle "abc" "defgh"将返回"adbecfgh"。或者shuffle "abc" ""返回​​。将Haskell中的两个列表随机混合在一起

到目前为止,我有:

shuffle xs ys = concatMap (\(x,y) -> [x,y]) (zip xs ys) 

的问题是,这只是洗牌名单最短列表的长度和不包括长列表的其余部分。所以shuffle "abc" "defgh"返回"adbecf"而不是"adbecfgh"

任何人都可以帮助我找到更好的方法吗?

+0

同样[交错名单列表](http://stackoverflow.com/questions/14186433/interleave-list-of -lists-in-haskell)类似,但更一般。 – phadej 2015-02-11 07:42:11

回答

9

你可以简单地提供一个逐点高清:

shuffle :: [a] -> [a] -> [a] 
shuffle [] ys = ys 
shuffle xs [] = xs 
shuffle (x:xs) (y:ys) = x : y : shuffle xs ys 

PreludeData.Listzip*方法是行不通的,因为他们将只需要较短的列表的长度。

7

另外,略短,这样做逐点,泽塔建议:

shuffle :: [a] -> [a] -> [a] 
shuffle [] ys = ys 
shuffle (x:xs) ys = x : shuffle ys xs