Skip to content

Instantly share code, notes, and snippets.

@retronym
Created December 11, 2009 07:16
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save retronym/254045 to your computer and use it in GitHub Desktop.
Save retronym/254045 to your computer and use it in GitHub Desktop.
Bind Type Class instance for scala.collection.traversable. It ain't pretty.
import collection._
import collection.generic._
trait Bind[Z[_]] {
def bind[A, B](a: Z[A], f: A => Z[B]): Z[B]
}
implicit def TraversableBind[M[X] <: Traversable[X]] = new Bind[M] {
def bind[A, B](r: M[A], f: A => M[B]): M[B] = {
implicit object cbf extends CanBuildFrom[Traversable[A], B, M[B]] {
def apply(from: Traversable[A]) = apply
def apply() = r.companion.newBuilder[B].asInstanceOf[collection.mutable.Builder[B, M[B]]]
}
r.flatMap[B, M[B]](f)
}
}
assert(implicitly[Bind[List]].bind(List(1, 2, 3), (x: Int) => List(x, x)) == List(1, 1, 2, 2, 3, 3))
assert(implicitly[Bind[Stream]].bind(Stream.continually(1), (x: Int) => Stream(x, -x)).take(3).toList == List(1, -1, 1))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment