モナド則
monad law
Monad型クラスのインスタンスとなる型が満たすべき条件
Monad型クラスのインスタンスになるだけでは本物のモナドとは呼べない
ただし、型クラスの実装に関してはコンパイラはチェックしてくれるが、モナド則を満たしているかどうかはチェックしてくれない
自力でチェックする必要がある
標準で入っているモナドは満たしている(はず)
Agda, Idris, Coqあたりの言語では外部ライブラリを用いてモナドが使え、モナド則もチェックしてくれるらしい
前提
出てくるものの型
mはMonad型クラスの型
code:hs
return :: a -> m a
(>>=) :: m a -> (a -> m b) -> m b
(>=>) :: (a -> m b) -> (b -> m c) -> (a -> m c)
f >=> g = \x -> f x >>= g
f :: a -> m a
1. 左恒等性
return が bind の左側単位元になっている
return x >>= f $ \equivf x
<=<、>=>を使って書き直すと
こっちが本質な気がするmrsekut.icon
f <=< return$ \equivf
return >=> f$ \equivf
2. 右恒等性
return が bind の右側単位元になっている
m >>= return $ \equivm
>>= returnはモナド値に対する恒等射
<=<、>=>を使って書き直すと
こっちが本質な気がするmrsekut.icon
return <=< f$ \equivf
f >=> return$ \equivf
3. bind の結合則
以下の等式が成り立つ
m >>= f >>= g$ \equivm >>= (\x -> f x >>= g)
連続のbindを、ラムダ関数とbindを使って書き直している
要するにモナド関数の結合法則が成り立つことを言っている
こっちが本質な気がするmrsekut.icon
((f >>= g) >>= h)$ \equiv(f >>= (g >>= h))
((f <=< g) <=< h)$ \equiv(f <=< (g <=< h))
(f >=> g) >=> h$ \equivf >=> (g >=> h)
完全に理解できていないのですごいH本.icon p.311読み直そう
bindの向きを逆にしたもの
code:hs
return :: a -> M a
(=<<) :: (a -> M b) -> (M a -> M b)
(=<<) return t = t
(=<<) f (return a) = f a
(=<<) g (((=<<) f) t) = (=<<) (\a -> (=<<) g (f a)) t
具体例
1の左恒等性をMaybeで見てみる
code:hs
f :: Int -> Maybe Int
f x = Just (x+1)
return 3 >>= f -- Just 4
Just 3 >>= f -- Just 4
f x -- Just 4
定義よりMaybeではreturnとJustは同じ
1の左恒等性をListで見てみる
code:hs
f :: Int -> Int
f x = x, x, x
return 3 >>= f -- 3,3,3
3 >>= f -- 3,3,3
f 3 -- 3,3,3
2の右恒等性を見てみる
code:hs
-- List
1,2,3 >>= return -- 1,2,3
-- Maybe
Just 3 >>= return -- Just 3
Nothing >>= return -- Nothing
モノイド則、通常の関数との対応
code:モナド則.hs
return >=> f == f -- 左恒等性
f >=> return == f -- 右恒等性
(f >=> g) >=> h == f >=> (g >=> h) -- 結合法則
code:モノイド則.hs
mempty <> a == a -- 左恒等性
a <> mempty == a -- 右恒等性
(a <> b) <> c == a <> (b <> c) -- 結合法則
code:通常の関数.hs
id . f == f -- 左恒等性
f . id == f -- 右恒等性
(f . g) . h == f . (g . h) -- 結合法則
https://qiita.com/hiratara/items/9a78540698943009ebc7
参考
結局、モナド則は何を要求しているのか - Qiita
https://aratama.github.io/purescript/chapter08.html
8.5
https://qiita.com/ruicc/items/109692ea1df502d20666