On Tue, Feb 2, 2010 at 20:25, David Menendez wrote: > On Tue, Feb 2, 2010 at 1:48 PM, Ryan Ingram wrote: > > Gen slightly breaks the monad laws: > > > >> arbitrary >>= return > > is not the same as > >> return () >>= const arbitrary > > because each bind splits the generator, so you end up with a different > > seed passed to arbitrary in these two cases. >
Ah yes, that was exactly the problem. > > If the observable value is "some random object" this is a safe fudge, > > but if you want repeatable, it doesn't quite work. You need your > > instances to be exactly identical, down to the associativity of binds, > > in order to get the same results. > > We could avoid that problem by redefining Gen as a state transformer monad. > > newtype Gen a = MkGen { unGen :: StdGen -> Int -> (a, StdGen) } > > instance Monad Gen where > return a = MkGen $ \r _ -> (a,r) > MkGen m >>= k = MkGen $ \r n -> let (a,r') = m r n in unGen (k a) r' n > > I'm pretty sure all the Gen primitives can be similarly redefined. > And I'm guessing I haven't been or won't be the only one running into this issue. Sean
_______________________________________________ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe