当前位置:  开发笔记 > 编程语言 > 正文

如何在使用scalaz时为布尔创建半群?

如何解决《如何在使用scalaz时为布尔创建半群?》经验,为你挑选了1个好方法。

我使用scalaz进行一些验证,在代码中的某处有布尔条件.示例如下所示:

import scalaz._, std.AllInstances._

object Temporary {

  def validate(x: Int): scalaz.Validation[List[String], Boolean] = {
    try {
      if (x < 10) {
        scalaz.Success(true)
      } else {
        throw new RuntimeException("why oh why")
      }
    } catch {
      case e: Throwable => scalaz.Failure(List(e.getMessage))
    }
  }


  def main(args: Array[String]) {
    val x = validate(1) +++ validate(10)
    println(x)

    val y = List(1,2,4,10).map(validate(_)).reduce(_ +++ _)
    println(y)
  }

}

我得到以下编译错误.

Error:(21, 25) could not find implicit value for parameter M1: scalaz.Semigroup[Boolean]
    val x = validate(1) +++ validate(10)
                        ^

我无法弄清楚如何解决此错误.有什么指针吗?

编辑

感谢@Travis Brown的回答,以下是为此示例修复的内容.我在对象中添加了这两行

  import scalaz.Semigroup, scalaz.std.anyVal.booleanInstance.conjunction
  implicit val booleanSemigroup: Semigroup[Boolean] = conjunction

现在它提供了正确的验证:

Failure(List(why oh why))
Failure(List(why oh why))

非常酷!



1> Travis Brown..:

可以说,对于布尔运算来说,并不是一个独特的半群 - 连词和析取都是追加操作的候选者 - 所以Scalaz没有提供Semigroup[Boolean].它确实提供ConjunctionDisjunction标记,如果将标记添加到Boolean值的静态类型(没有运行时开销),则可以获取指定操作的实例:

import scalaz.{ @@, Validation }
import scalaz.Tags.Conjunction

object Temporary {

  def validate(x: Int): Validation[List[String], Boolean @@ Conjunction] = {
    try {
      if (x < 10) {
        scalaz.Success(Conjunction(true))
      } else {
        throw new RuntimeException("why oh why")
      }
    } catch {
      case e: Throwable => scalaz.Failure(List(e.getMessage))
    }
  }

  def main(args: Array[String]) {
    val x = validate(1) +++ validate(10)
    println(x)

    val y = List(1,2,4,10).map(validate(_)).reduce(_ +++ _)
    println(y)
  }
}

如果你真的,真的想选择其中一个操作作为布尔运算半群操作,你可以这样做:

import scalaz.Semigroup, scalaz.std.anyVal.booleanInstance.conjunction

implicit val booleanSemigroup: Semigroup[Boolean] = conjunction

然后:

scala> import scalaz.syntax.semigroup._
import scalaz.syntax.semigroup._

scala> true |+| false
res1: Boolean = false

不过,这与Scalaz哲学有些不一致.

推荐阅读
小妖694_807
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有