Consider building a chessboard through binds (example lifted from Dustin Getz's pymonads).
Adapting that code to pynads implementation should look like this:
from pynads import List
def chessboard(ranks, files):
return List(*ranks) >> (lambda r:
List(*files) >> (lambda f:
List.unit((r,f)) ))
chessboard('abcedfgh', range(1,9))
Instead of getting List(('a', 1), ('a', 2), ...) we'll receive List('a', 1, 'a', 2, ...). This is in part to List.unit trying to be cute and convert iterables straight into a List monad rather than allowing a List monad containing an iterable. Where as with Haskell this results in [[1]]
test :: a -> [a]
test a = return a
test [1]
Moreover, simply removing the check on unit results in: List(<itertools.chain object at ...>)
Going further, and using the splat operator in List.bind results in this monster: List(List(List(('a',1)), List(('a',2)), ...), List(List(('b', 1)), ... ), ...)
Which is clearly not what's intended at all. Rather we're looking for: List(('a', 1), ('a', 2), ...).
I propose that pynads.List is fundamentally flawed and should be rewritten to mimic Haskell's behavior rather than attempting whatever it's doing now.
Consider building a chessboard through binds (example lifted from Dustin Getz's pymonads).
Adapting that code to pynads implementation should look like this:
Instead of getting
List(('a', 1), ('a', 2), ...)
we'll receiveList('a', 1, 'a', 2, ...)
. This is in part toList.unit
trying to be cute and convert iterables straight into a List monad rather than allowing a List monad containing an iterable. Where as with Haskell this results in[[1]]
Moreover, simply removing the check on unit results in:
List(<itertools.chain object at ...>)
Going further, and using the splat operator in
List.bind
results in this monster:List(List(List(('a',1)), List(('a',2)), ...), List(List(('b', 1)), ... ), ...)
Which is clearly not what's intended at all. Rather we're looking for:
List(('a', 1), ('a', 2), ...)
.I propose that pynads.List is fundamentally flawed and should be rewritten to mimic Haskell's behavior rather than attempting whatever it's doing now.