モナド則
monad law
Monad
型クラスのインスタンスになるだけでは本物のモナドとは呼べない
ただし、型クラスの実装に関してはコンパイラはチェックしてくれるが、モナド則を満たしているかどうかはチェックしてくれない
自力でチェックする必要がある
標準で入っているモナドは満たしている(はず)
前提
出てくるものの型
m
は Monad
型クラスの型
hsreturn :: 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
\equiv f x
<=<
、 >=>
を使って書き直すと
こっちが本質な気がする

f <=< return
\equiv f
return >=> f
\equiv f
2. 右恒等性
return が bind の右側単位元になっている
m >>= return
\equiv m
>>= return
はモナド値に対する恒等射
<=<
、 >=>
を使って書き直すと
こっちが本質な気がする

return <=< f
\equiv f
f >=> return
\equiv f
3. bind の結合則
以下の等式が成り立つ
m >>= f >>= g
\equiv m >>= (\x -> f x >>= g)
連続のbindを、ラムダ関数とbindを使って書き直している
要するにモナド関数の結合法則が成り立つことを言っている
こっちが本質な気がする

((f >>= g) >>= h)
\equiv (f >>= (g >>= h))
((f <=< g) <=< h)
\equiv (f <=< (g <=< h))
(f >=> g) >=> h
\equiv f >=> (g >=> h)
完全に理解できていないので

p.311読み直そう
bindの向きを逆にしたもの
hsreturn :: 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で見てみる
hsf :: 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で見てみる
hsf :: Int -> [Int]
f x = [x, x, x]
return 3 >>= f -- [3,3,3]
[3] >>= f -- [3,3,3]
f 3 -- [3,3,3]
2の右恒等性を見てみる
hs-- List
[1,2,3] >>= return -- [1,2,3]
-- Maybe
Just 3 >>= return -- Just 3
Nothing >>= return -- Nothing
モナド則.hsreturn >=> f == f -- 左恒等性
f >=> return == f -- 右恒等性
(f >=> g) >=> h == f >=> (g >=> h) -- 結合法則
モノイド則.hsmempty <> a == a -- 左恒等性
a <> mempty == a -- 右恒等性
(a <> b) <> c == a <> (b <> c) -- 結合法則
通常の関数.hsid . f == f -- 左恒等性
f . id == f -- 右恒等性
(f . g) . h == f . (g . h) -- 結合法則
参考
8.5