Identity Monad
HaskellのIdentity Monadは、値をそのまま保持する非常にシンプルなMonadです。以下はIdentity Monadの定義とインスタンスです。
newtype Idnty a = Idnty { runIdnty :: a }
instance Functor Idnty where
fmap f (Idnty x) = Idnty (f x)
instance Applicative Idnty where
pure a = Idnty a
(Idnty f) <*> (Idnty x) = Idnty (f x)
instance Monad Idnty where
(Idnty m) >>= k = k m
Identity Monadの重要な点は以下の通りです。
-
newtype Idnty a = Idnty { runIdnty :: a }Identityは値をそのまま保持します。この型はa型の値をIdnty型でラップします。 -
instance Monad Idnty whereIdentityはMonadの法律に準拠します。bind操作は内部の値を取り出してそのまま次の関数に渡します。
Identity MonadのMonad法律の証明:
-
return a >>= f ≡ f areturn aはIdnty aです。bind操作はこの値を取り出してfに渡します。 -
m >>= return ≡ m内部の値を取り出してそのままreturnに入れると、元の値がそのまま保持されます。 -
(m >>= f) >>= g ≡ m >>= (\x -> f x >>= g)内部の値が正しく伝搬され、Monadの結合性が保たれます。
IdentityT Monad Transformer
IdentityTはMonad Transformerです。他のMonadをラップし、その上でMonadの機能を提供します。
newtype IdntyT m a = IdntyT { runIdntyT :: m a }
instance (Monad m) => Monad (IdntyT m) where
return a = IdntyT (return a)
(IdntyT m) >>= k = IdntyT (m >>= (runIdntyT . k))
instance MonadTrans IdntyT where
lift = IdntyT
instance (MonadIO m) => MonadIO (IdntyT m) where
liftIO = IdntyT . liftIO
IdentityTの重要な点は以下の通りです。
-
newtype IdntyT m a = IdntyT { runIdntyT :: m a }IdentityTは内部のMonadmをラップします。値はm a型で保持されます。 -
instance (Monad m) => Monad (IdntyT m) whereIdentityTは内部のMonadmの上にMonadの機能を提供します。
IdentityTのMonad法律の証明:
-
return a >>= f ≡ f areturnは内部のMonadのreturnを使用します。 -
m >>= return ≡ m内部のMonadのreturnを使用すると、値がそのまま保持されます。 -
(m >>= f) >>= g ≡ m >>= (\x -> f x >>= g)内部のMonadの結合性が保たれます。
IdentityTのMonad Transformerとしての性質
IdentityTはMonad Transformerの基本的な性質を持ちます。特に、lift関数の定義はMonad Transformerの法律を満たします。
-
lift . return ≡ returnliftは内部のMonadのreturnをそのまま使用します。 -
lift (m >>= f) ≡ lift m >>= (lift . f)内部のMonadのbind操作が正しく伝搬されます。