Examples
CPS, Continuation Monad, and Writer Monad の例。
part :: (a -> Bool) -> [a] -> [a] part p l = let f [] z = z f (x:xs) z = if p x then x : f xs z else f xs (z++[x]) in f l []
をいろいろに書いてみる*1。
Continuation Monad
外に吐き出すためにmapContを使う。
part1' p xs = runCont (f xs) id where f [] = return [] f (x:xs) | p x = mapCont (x:) $ f xs | otherwise = f xs >>= return . (x:)
右結合
条件を充たさない方のリストも右結合になっている。
part2 p xs = uncurry ($) $ f xs where f [] = (id, []) f (x:xs) | p x = appFst ((x:) .) $ f xs | otherwise = appSnd (x:) $ f xs appFst f ~(x, y) = (f x, y) appSnd f ~(x, y) = (x, f y)
Writer Monad
part2' p xs = r where (r, w) = runWriter $ f xs f [] = return w f (x:xs) | p x = f xs >>= return . (x:) | otherwise = tell [x] >> f xs
おまけ
part0 p = uncurry (++) . partition p
*1:[id:yokoyamatetsuo:20050219#p5]より
*2:論文は読んでないけれど多分vanish_appがやっていること