【发布时间】:2016-12-07 16:41:09
【问题描述】:
可以像这样使用显式字典传递重新绑定 (>>=) 并返回一个 monad:
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE RebindableSyntax #-}
module Lib where
import Prelude hiding ((>>=), return)
data MonadDict m = MonadDict {
bind :: forall a b. m a -> (a -> m b) -> m b ,
ret :: forall a. a -> m a }
(>>=) :: (MonadDict m -> m a) -> (a -> (MonadDict m -> m b)) -> (MonadDict m -> m b)
return :: a -> (MonadDict m -> m a)
monadDictIO :: MonadDict IO
usage = let
monadicCode = do
ln <- const getLine
const . putStrLn $ ln
in monadicCode monadDictIO
有没有更好的方法,如何表示 monad,以便避免在每次使用 monadic 动作时忽略 MonadDict monad 实例参数(使用 const)?
【问题讨论】:
-
你肯定会想要更像
(>>=) :: MonadDict m -> m a -> (a -> m b) -> m b的东西,或者如果你得到三个不同的字典你打算怎么做? -
@DanielWagner 我只用过一次看到
usage部分,我在最后通过字典 -
通常简单的不变量,如“我只通过一个”,要求类型检查器为您检查是件好事。我提出的类型是要求它这样做的一种方式。
-
@DanielWagner 你如何将多个
MonadDict ms 传递给>>=;只暴露了一个,最后一个MonadDict m参数;只要>>=将该读者的参数传递给其他两个读者,相同的字典将用于所有3。(>>=)的类型与ReaderT (MonadDict m) m的前奏曲(>>=)相同,但有不同实施。 -
@Cirdec 啊,你是对的:我完全误读了类型签名!
标签: haskell monads typeclass do-notation