scala> val f = (i : Int) => List(i + "F", i + "G")f: (Int) => List[String] = <function1>scala> 1.some traverse fres3: List[Option[String]] = List(Some(1F), Some(1G))
scala> none[Int] traverse fres4: List[Option[String]] = List(None)
scala> val f = (i : Int) => nil[String]f: (Int) => List[String] = <function1>scala> none[Int] traverse fres8: List[Option[String]] = List(None)scala> 1.some traverse fres9: List[Option[String]] = List()
This is correct behaviour of the traverse function. Have you seen The
Essence of the Iterate Pattern?
* http://www.comlab.ox.ac.uk/jeremy.gibbons/publications/iterator.pdf
* http://etorreborre.blogspot.com/2011/06/essence-of-iterator-pattern.html
- --
Tony Morris
http://tmorris.net/
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.10 (GNU/Linux)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org/
iEYEARECAAYFAk4LnMcACgkQmnpgrYe6r60G4QCffErFu1b0ffsTXFtS1NsdU8ek
sjYAn00TVmB1xcTcl2UEPNZrWu1X72bi
=Eb8K
-----END PGP SIGNATURE-----
none[A] traverse f == List(None) ∀ f : A => List[B]
--
You received this message because you are subscribed to the Google Groups "scalaz" group.
To post to this group, send email to sca...@googlegroups.com.
To unsubscribe from this group, send email to scalaz+un...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/scalaz?hl=en.
Why are you expecting an empty list? That's the real question.
Traverse can't know anything about your functor other than that it's
applicative. It doesn't know that there's such a thing as the empty
list. It necessarily preserves the structure of whatever your
traversal returns.
> Say what? If I traverse nothing, I end up with more results than if I
> traversed something... Can someone explain why any of this makes sense,
Again, the structure of the traversal is always preserved. If your
traversal returns empty lists, you will end up with empty lists.
Here's my suggestion: Try writing traverse yourself. This will give
you a good understanding of how it actually works and why.
--
You received this message because you are subscribed to the Google Groups "scalaz" group.
That's clear, but it might be instructive to look into what
assumptions are causing you to expect something other than what you
get.
> Difficult to write something when you don't have a feel for what on earth it
> is supposed to do. I know the answer is in the types, btw :-)
Definitely try to puzzle through it. When you look at the types in
this signature, there are a few things you know right off the bat:
def traverse[M[_]:Applicative, A, B](oa: Option[A], f: A => M[B]):
M[Option[B]] =
1. It's easy to exhaustively list everything that is in scope.
You have your arguments:
oa : Option[A]
f : A => M[B]
And an implicit argument of type Applicative[M].
2. You cannot deconstruct f any further, so you should probably
proceed by looking at oa. There are only two cases for oa, either it's
None, or Some(a). If it's None, you know how to put it in M (you can
put any value in M because you have Applicative[M]). If it's Some(a),
you can apply f(a) and put the resulting B inside Some.
Note that producing an empty M is not one of the things you can do.
The instances of Traverse provided in Scalaz fall into two groups:
those that use Applicative[M].apply (List, Tree, Zipper, ...), and
those that only need Pointed[M] (Option, Either, Function0, ...).
Seems like an interesting property, does it have a name?
-jason