Haskell 如何实现mapAccumM?
我想要Haskell 如何实现mapAccumM?,haskell,Haskell,我想要mapM在传递累加器时可以遍历的东西上。我想到了: import Control.Applicative import Data.Traversable import Control.Monad.State mapAccumM :: (Applicative m, Traversable t, MonadState s m) => (s -> a -> m (s, b)) -> s -> t a -> m (t b) mapA
mapM
在传递累加器时可以遍历的东西上。我想到了:
import Control.Applicative
import Data.Traversable
import Control.Monad.State
mapAccumM :: (Applicative m, Traversable t, MonadState s m)
=> (s -> a -> m (s, b)) -> s -> t a -> m (t b)
mapAccumM f acc0 xs = put acc0 >> traverse g xs
where
g x = do
oldAcc <- get
(newAcc, y) <- f oldAcc x
put newAcc
return y
导入控件。应用程序
导入数据。可遍历
进口控制单体状态
mapAccumM::(应用程序m,可遍历t,单态s m)
=>(s->a->m(s,b))->s->t a->m(t b)
mapAccumM f acc0 xs=put acc0>>遍历g xs
哪里
gx=do
oldAccroconnor在哈斯克尔为我回答了这个问题
这解决了我的问题,但请注意,累加器在元组的第二个元素而不是第一个元素中返回
mapAccumM :: (Monad m, Functor m, Traversable t) => (a -> b -> m (c, a)) -> a -> t b -> m (t c)
mapAccumM f = flip (evalStateT . (Data.Traversable.traverse (StateT . (flip f))))
或返回蓄能器:
mapAccumM' :: (Monad m, Functor m, Traversable t) => (a -> b -> m (c, a)) -> a -> t b -> m (t c, a)
mapAccumM' f = flip (runStateT . (Data.Traversable.traverse (StateT . (flip f))))
你可以在你的函数中使用StateT
和runStateT
,而不要求外部monad是一个状态monad…说清楚了,你想要与monad m
限制相同的类型,而不是MonadState s m
?ChrisTaylor:是的,我想要monad,不确定状态monad转换器是否算作“无状态单子”;D