2012-06-04 46 views
3

我烏德的印象是驗證可以作爲一個Monoid /半羣 我試圖在斯卡拉2.9.2和scalaz 7快照下面的代碼驗證是一個SemiGroup/Monoid:使用| + |不工作

import scalaz._ 
import Scalaz._ 

val success1 = 1.success 
val success2 = 2.success 

val failureA = "A".fail 
val failureB = "B".fail 

success1 |+| success2 
<console>:16: error: diverging implicit expansion for type scalaz.Semigroup[scalaz.Validation[Nothing,Int]] 
starting with method validationSemigroup in trait ValidationInstances 
       success1 |+| success2 
      ^
<console>:16: error: value |+| is not a member of scalaz.Validation[Nothing,Int] 

       success1 |+| success2 

我期待一個Success(3)

然後

failureA |+| failureBres1: scalaz.Validation[java.lang.String,Nothing] = Failure(AB) 預期

success1 |+| failureA

<console>:16: error: diverging implicit expansion for type scalaz.Semigroup[scalaz.Validation[Nothing,Int]] 
starting with method validationSemigroup in trait ValidationInstances 
       success1 |+| failureA 
      ^
<console>:16: error: value |+| is not a member of scalaz.Validation[Nothing,Int] 

       success1 |+| failureA 

預計爲什麼|+|Success不起作用失敗?它是一個錯誤還是我錯過這裏

回答

3

東西它的工作原理是這樣的:

scala> import scalaz._, Scalaz._ 
import scalaz._ 
import Scalaz._ 

scala> val success1 = 1.success[String] 
success1: scalaz.Validation[String,Int] = Success(1) 

scala> val success2 = 2.success[String] 
success2: scalaz.Validation[String,Int] = Success(2) 

scala> val failureA = "A".fail[Int] 
failureA: scalaz.Validation[java.lang.String,Int] = Failure(A) 

scala> val failureB = "B".fail[Int] 
failureB: scalaz.Validation[java.lang.String,Int] = Failure(B) 

scala> success1 |+| success2 
res0: scalaz.Validation[String,Int] = Success(1) 

scala> failureA |+| failureB 
res1: scalaz.Validation[java.lang.String,Int] = Failure(AB) 

scala> success1 |+| failureA 
res2: scalaz.Validation[String,Int] = Success(1) 

你沒有在你的前兩個val的指定左邊元素(Failure)的類型。這就是爲什麼Nothing被推斷。顯然,如果左元素是SemigroupNothing不是,String是),則Validation具有Semigroup實例。這是一個instance

UPD:而且,正如你看到的,Semigroup實例就獲得第一Success而不是使用Success「ES Semigroup實例。我看到,有一個方法appendValidation,這需要左,右元素是Semigroup S和使用這兩個實例:

scala> success1 append success2 
res6: scalaz.Validation[String,Int] = Success(3) 

不知道,爲什麼不ValidationSemigroup實例使用。創建pull request以更改此行爲。