なんとなく理解するモナドとアプリカティブ
from Implementation: Working with Errors
モナディック関数
「通常」の値を受け取り、ある種の「拡張」された値を返す関数
Result を生成する関数の連鎖(bind と errorMap、map) に当てはめて考える
「拡張」された値 = Result 型でラップされた値
したがって、モナディック関数 = スイッチ関数
https://scrapbox.io/files/66af628d724792001c02f4f6.png
モナド
モナディック関数 を直列につなげることができるもの
アプリカティブ をより抽象化した概念
コンテキスト(コンテナ)の中の値に基づいて、新しいコンテキストを生成する
技術的には、3 つの要素を持つ
データ構造
e.g. Result
関連するいくつかの関数
return(pure)
「通常」の値を「拡張」された値に変換する関数
Result の場合、Ok コンストラクタがこれに該当する
bind(flatMap)
モナディック関数を連鎖させるための関数
Result の場合
code:fsharp
let bind f aResult =
match aResult with
| Ok success -> f success
| Error failure -> Error failure
関数がどのように動作しなければならないかを定めるルール
モナド則(Haskell)
code:haskell
return x >>= f = f x
mx >>= return = mx
(mx >>= f) >>= g = mx >>= (\x -> (f x >>= g))
モナディックスタイル
bind を用いて、モナディック関数 を直列に連結する記述方法
code:haskell
do
x1 <- m1
x2 <- m2
.
.
.
xn <- mn
f x1 x2 ... xn
アプリカティブ
モナディック関数 を並列に組み合わせることができるもの
ファンクタ をより抽象化した概念
アプリカティブスタイル
apply (<*>)を用いて、モナディック関数 を並列に組み合わせる記述方法
code:haskell
pure g <*> x1 <*> x2 <*> ... <*> xn
(<*>) :: Applicative f => f (a -> b) -> f a -> f b
アプリカティブを用いると、複数エラーを同時(並列)に扱うことができる
関連
Monad は継続、Applicative は並列