所以基本上我有一个计算step
,它接受以前的结果并输出 a Rand g Path
,其中Path
是一个自定义数据类型(把它想象成一个旅行推销员的问题)。我让MonadRandom
处理所有的生成器传递和东西。
我想自己找到这个计算的第 n 个组成。现在我正在使用
thecomputation :: (RandomGen g) => Rand g Path
thecomputation = (iterate (>>= step) (return startingPath)) !! n
然后打印出来我会跑
main = do
res <- evalRandIO thecomputation
print res
但是,我有一个问题
如果我选择一个足够高的n
值(我需要 10^6 的数量级),我会得到一个堆栈溢出。
我已经设法将问题跟踪到计算实际上是一个高度组合(嵌套?)的 IO 对象这一事实。这是一系列 IO 计算,因此 ghc 必须跟踪所有嵌套 IO 层,并且在足够层之后,它放弃了。
我该怎么处理这个?在命令式语言中,这真的没什么。但是我应该在这里做什么?我应该强迫一些 IO 评估还是……?
这个网站上有一个类似的问题,但我无法从接受的答案中得到任何帮助,所以我仍然很迷茫
具体例子
import System.Random
import Control.Monad.Random
import Control.Monad
data Path = DoublePath Double deriving Show
step :: (RandomGen g) => Path -> Rand g Path
step (DoublePath x) = do
dx <- getRandom
return (DoublePath ((x + dx)/x))
thecomputation :: (RandomGen g) => Rand g Path
thecomputation = (iterate (>>= step) (return (DoublePath 10.0))) !! 1000000
main = do
result <- evalRandIO thecomputation
print result
在我的电脑上溢出