I am struggling to understand the following function definition in Traverse
trait in Scalaz:
def traverse[F[_] : Applicative, A, B](f: A => F[B], t: T[A]): F[T[B]]
The part I don't understand is F[_] : Applicative
.
Now, let's see what Applicative
is:
trait Applicative[Z[_]] extends Pointed[Z] with Apply[Z] {
override def fmap[A, B](fa: Z[A], f: A => B): Z[B] = this(pure(f), fa)
override def apply[A, B](f: Z[A => B], a: Z[A]): Z[B] = liftA2(f, a, (_:A => B)(_: A))
def liftA2[A, B, C](a: Z[A], b: Z[B], f: (A, B) => C): Z[C] = apply(fmap(a, f.curried), b)
}
Here, for traverse
to work for some type F
, one needs to bring an implicit object of type Applicative[F]
in scope.
I'd like to understand several things:
F[_] : Applicative
mean?F[_]
has something to do with Applicative
? We need Applicative[F]
, not F[something] extends Applicative right?Applicative[F]
without declaring implicit parameters?I think all three questions can be answered with the fact that this notation:
def traverse[F[_] : Applicative, A, B](f: A => F[B], t: T[A]): F[T[B]]
is equivalent to this:
def traverse[F[_], A, B](f: A => F[B], t: T[A])(implicit $ev: Applicative[F]): F[T[B]]
The first notation is known as a context bound for F[_]
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With