[Haskell-cafe] How to use randomized algorithm within the implementation of pure data structures?
Bardur Arantsson
spam at scientician.net
Sat Nov 1 10:16:02 UTC 2014
On 2014-11-01 10:25, Hiromi ISHII wrote:
> Hi cafe,
>
> I'm currently implementing the data structure representing algebraic numbers.
>
> Implementing algebraic number arithmetic requires polynomial factorisation.
> Pure algorithm for factoring (Berlekamp's algorithm) is more expensive than
> the randomized one (Cantor-Zassenhaus algorithm) , so I want to use the
> latter algorithm.
>
> Since C-Z algorithm is a randomized algorithm, we have to have an access
> for random number generator when calculating algebraic number arithmetics
> e.g. writing Num instance for algebraic numbers.
>
> Here is the problem: how to pass-around random number generator throughout pure computaion?
>
> I think one immediate solution is to create global state with `newStdGen` and `unsafePerformIO` like below:
>
You can just use the State monad to thread the StdGen around and
"update" it when you need to. You can get a pure interface by hiding
away the runState behind a function:
-- The is the function you export from your module.
myAlgorithm :: StdGen -> ... -> ...
myAlgorithm g .... = fst . runState (myAlgorithm' ...) g
myAlgorithm' :: ... -> State StdGen Result
myAlgorithm' ... = do
...
x <- rand
...
return $ ...
rand :: State StdGen a
rand = do
x <- get
(a, g') <- random -- Here "random" is from System.Random
put $! g'
return a
(The above probably contains typos, and can probably also be prettified,
but hopefully you get the gist.)
Regards,
More information about the Haskell-Cafe
mailing list