Reputation:
I have the following validation logic:
def one(a : String) : Validation[String, Int] =
if (a == "one") {
Success(1)
} else {
Failure("Not One")
}
def two(a : String) : Validation[String, Int] =
if (a == "two") {
Success(2)
} else {
Failure("Not Two")
}
def validate (a : String) = (one(a) |@| two(a)){_ + _}
According to the Scalaz documentation:
/**
* DSL for constructing Applicative expressions.
*
* `(f1 |@| f2 |@| ... |@| fn)((v1, v2, ... vn) => ...)` is an alternative to `Apply[F].applyN(f1, f2, ..., fn)((v1, v2, ... vn) => ...)`
*
* `(f1 |@| f2 |@| ... |@| fn).tupled` is an alternative to `Apply[F].applyN(f1, f2, ..., fn)(TupleN.apply _)`
*
* Warning: each call to `|@|` leads to an allocation of wrapper object. For performance sensitive code, consider using
* [[scalaz.Apply]]`#applyN` directly.
*/
How do I convert the validate function to use apply2
?
Upvotes: 5
Views: 79
Reputation: 9698
Type constructor for Validate
takes two parameters, but Apply
can only be parameterized by a type constructor of arity one. You need a special trick called type lambda which allows us to curry the type definition:
def validate(a : String) = Apply[({type λ[Int] = Validation[String, Int]})#λ].apply2(one(a), two(a)){_ + _}
Upvotes: 5