2012-09-05 9 views
5

scala.Eitherがモナドとして行われなかった理由を知りたいと思っています。すでにどのように例えば、Eitherをバイアス右に上のいくつかの議論が存在する:Scalasはなぜモナドではないのですか?

は、しかし、あまりにも多くの詳細が記載されていると私は得ることができませんでしたそれが完了したときにそれがなぜ行われたかについての完全な概要。そのような問題や、偏ったEither(存在する場合でも)のメリットについては、誰かが右偏向の利点についての概要を教えてもらえますか?Either

+0

本当に質問に答えることはできませんが、あなたが探しているものと思われるScalazの「検証」をチェックすると多かれ少なかれです。印象的な例は – adelbertc

答えて

7

私はそれがちょうどPrinciple of Least Astonishmentになると思います。成功または失敗を符号化するためにEitherを使用することは明らかに人々が行うことですが、Eitherの唯一の使用ではありません。実際には、Rightを成功させる理由はほとんどなく、Leftは伝統以外の失敗であることはありません。上記のadelbertcのコメントのように、scalazにはValidationがあり、特にこれをエンコードしています。

はさらに、このコードを取る、上記POLAの主張を正当化するには:私はfor式で.right投影を使用していますので、

def foo(): Either[Int, Int] = Right(1) 
def bar(j: Int): Either[Int, Int] = Left(1) 
def baz(z: Int): Either[Int, Int] = Right(3) 

// Result is Left(1) 
for (a <- foo().right; b <- bar(a).right; c <- baz(b).right) yield c 

これがコンパイルされます。ここでLeft(1)barの場合は失敗のケースであり、その結果ですが、EitherRightの場合は想像してください。あなただけの「一または-その他」タイプであるためにあなたのコード内でEitherを使用した場合、あなたは(1で驚かれることでしょう

for (a <- foo(); b <- bar(a); c <- baz(b)) yield c 

:上記のコードは次のように表現で.right投影せずにコンパイルします)これがコンパイルされ、(2)Left(1)が返され、一見、bazを実行しないという事実。

要約すると、を使用して成功または失敗をエンコードする場合は、Validationを使用します。

+0

+1です。 – Frank

5

これが元の理由かどうかわかりませんが、少なくとも1つの正当な理由があります。 Scalaでは、forの解説は、完全な機能を得るためにはモナドであるよりも多くの議論が必要です。特に、モナドはモナド-とゼロ(条件が失敗した場合ので、あなたがそれを空にすることができます)であることを必要とし

for (a <- ma if a > 7; /*...*/) yield /*...*/ 

のような構築物があります。

Eitherは、ゼロでモナドにすることはできません(Either[Unit,B]の場合は、Left(())はゼロにすることができます)。

行く方法の1つは、大丈夫です、ちょうどそのような方法であなたのためにあなたのための理解を使用しないでください。行く別の方法は言うことができます:大丈夫、大丈夫、すべてのモナドを作る気にしないでください。もちろん、個人的な好みの問題ですが、フルパワーを使用しようとすると、Either(Scalaで提供される共通のモナドの中で一意に)が平坦になることで、ある程度エレガンスが失われていることがわかりますforがあなたに与えます。