- 作者: Martin Odersky,Lex Spoon,Bill Venners,羽生田栄一,水島宏太,長尾高弘
- 出版社/メーカー: インプレスジャパン
- 発売日: 2011/09/27
- メディア: 単行本(ソフトカバー)
- 購入: 12人 クリック: 235回
- この商品を含むブログ (46件) を見る
一部不正確とは
「MonadとMonadPlusを区別していなくて、witFilterメソッドの実装がMonadに対して必須のように書いてある」
ということです。
以下それの解説的なものを少し書きますが、上記の一文で意味わかる人はこれ以降読まなくていいと思います
ちょっと長くなるけど引用。第2版の450ページ
map、flatMap、withFilterは、モナドの演算として定式化できる。そうした定式化により、上に示した型を正確に持てるようになる。さらに、あらゆるモナドは、map、flatMap、withFilterの3つ、さらに「ユニット」コンストラクター(要素値からモナドを作るもの)によって特徴づけられる。
中略
map、flatMap、withFilterは、モナドという関数型概念のオブジェクト指向版と見ることができる。これらの3つのメソッドによって書き換えられるfor式は、モナドのための構文と考えることができる。
明らかに、「モナド」の部分を「モナドプラス」にするか、そうでないならwithFilterを除いたほうが正確だと思います。*1
念のため英語版*2も少し確認してみましたが
http://www.artima.com/pins1ed/for-expressions-revisited.html#23.6
訳の間違いなどではなく、英語版も同じように書かれてますね。
MonadPlusとfilterの関係は以前ちょっと書きました。
HaskellのdoとScalaのfor式とEitherとMonadPlus
これ↑ではEitherのこと話しましたが、他にもMonadとMoandPlusの違いの理解のために、
「Monadにはなるけど、MonadPlusにはならない」ものを例として上げると、NonEmptyListというのがあります(標準ライブラリではなくScalazのものです、すいません)
https://github.com/scalaz/scalaz/blob/v7.0.0/core/src/main/scala/scalaz/NonEmptyList.scala
「要素を1つ以上保持している」ことが保証されることが特徴で、それ以外は普通のListと変わりません(つまり片方向リンクリスト)
証明とかではなく
「NonEmptyListがMonadPlusではない=>つまり(自然な)filterメソッドを定義できない」
ことに対する直感的な(?)説明をしてみると、
「要素を1つ以上保持していることが保証されなければならない」のに、もしfilterしていき1つも当てはまるものがなくなったらどうするの?となりますよね?(例外投げるとか?)なので、NonEmptyListはMonadですが、MonadPlusではありません。でも、for式で*3使えます。
もう一度まとめておくと、ScalaのforはflatMapとmapを正しく実装できた場合は「Monadのための記法」になりますし、それに加えてwithFilter*4を実装できれば「MonadPlusのための記法」です。
細かいことのようですが、これを区別できるとき、区別する必要があるときは、ちゃんと区別して話しましょう。