ApplicativeBuilder的优点是什么?

时间:2015-04-20 06:25:49

标签: scalaz applicative

Applicative提供“operator”<*>,我可以按如下方式使用:

val f: (Int, Int) => Int = {(x, y) => x + y}
1.some <*> (2.some <*> f.curried.some)

除了scalaz提供ApplicativeBuilder

之外
(1.some |@| 2.some)(f)

ApplicativeBuilder有什么好处?您何时会使用|@|代替<*>

2 个答案:

答案 0 :(得分:3)

更好的类型推断

scala> ^(1.right[String], 2.right[String])(_ + _)
<console>:16: error: type mismatch;
 found   : scalaz.\/[String,Int]
 required: ?F[?A]
Note that implicit conversions are not applicable because they are ambiguous:
 both method ToAssociativeOps in trait ToAssociativeOps of type [F[_, _], A, B](v: F[A,B])(implicit F0: scalaz.Associative[F])scalaz.syntax.AssociativeOps[F,A,B]
 and method ToBitraverseOps in trait ToBitraverseOps of type [F[_, _], A, B](v: F[A,B])(implicit F0: scalaz.Bitraverse[F])scalaz.syntax.BitraverseOps[F,A,B]
 are possible conversion functions from scalaz.\/[String,Int] to ?F[?A]
              ^(1.right[String], 2.right[String])(_ + _)
                                                 ^

scala> (1.right[String] |@| 2.right[String])(_ + _)
res1: scalaz.\/[String,Int] = \/-(3)

答案 1 :(得分:0)

一方面没有其他优点,但正如你所看到的那样,Applicative Builder并不需要,你的功能是在F的背景下进行的。在我看来,它的括号使用方式更加平易近人。

您还可以说Applicative Builder构建临时对象,因此在使用性能非常关键的代码和/或循环时,您应该避免使用它。在这种情况下,您可以使用其他替代方法,例如:Applicative[Option].apply2(3.some, 4.some)(f)。这又与|@|语法非常接近,只是您不必计算要为f(n1, n2, ...)提供的参数数量。