haskell提升操作
Monad在haskell中是非常常见的操作,一个函数要在不同的Monad中工作就离不开lift。
lift
来自 MonadTrans 类,当使用 Monad Transformer(如 StateT, ReaderT, MaybeT 等)时,操作底层 Monad(例如 IO)需要用 lift。
1 | lift :: Monad m => m a -> t m a |
1 | import Control.Monad.Trans.Class (lift) |
liftM
是 fmap 的一个特化,用于 Monad,而不是 Functor。将一个二元函数提升为Monad操作
1 | liftM :: Monad m => (a -> b) -> m a -> m b |
1 | import Control.Monad (liftM) |
(+1)操作本来接收一个Int,提升后可以接收一个IO Int
在 GHC 7.10 后,Applicative 成为了 Monad 的超类,因此可以直接用 fmap,推荐用 fmap 或 <$> 而不是 liftM。
1 | import Control.Monad (liftM) |
liftA
liftA 针对的是 Applicative,而 liftM 针对的是 Monad。由于 Monad 是 Applicative 的子类,现在两者的功能重叠,通常用 <$>。
liftIO
用于将 IO 操作提升到任何支持 MonadIO 的 Monad 中
1 | liftIO :: MonadIO m => IO a -> m a |
1 | import Control.Monad.IO.Class (liftIO) |
liftHandler
yesod框架用于提升handler到另一个Monad中
1 | class (MonadResource m, MonadLogger m) => MonadHandler m where |