gpt4 book ai didi

haskell - 跟踪 `map` 的进度

转载 作者:行者123 更新时间:2023-12-04 02:26:18 25 4
gpt4 key购买 nike

我有一个 map操作(实际上是使用 parMap 中的 Control.Parallel.Strategies 并行运行),这需要相当长的时间。鉴于我知道该函数被应用了多少次(在此上下文中为 n),我怎样才能每隔一段时间轻松地显示 n 中有多少次?申请是否经过评估?

显而易见的解决方案是将 map 设为 mapM与一些 putStr在映射函数内部,但这会:

  • 采取不必要的效率
  • 不是每隔一段时间就对状态进行采样,而是在每个应用程序中采样
  • 基本上消除了并行上下文中确定性算法的所有优点

  • 那么,有没有办法跟踪我丢失的这些信息,从而避免这些问题?

    最佳答案

    在生产环境中,您可能不应该使用跟踪并被迫处理需要 IO 的复杂性,但对于测试,您可以修改 parMap 的定义以采用另一个参数来告知何时发出计数:

    import Control.Monad (sequence)
    import Control.Parallel.Strategies (Strategy, using, rseq, rparWith, parMap)
    import Debug.Trace (traceShow)
    import System.IO (hFlush, hSetBuffering, BufferMode(NoBuffering), stdout)

    evalList' :: Integer -> Strategy a -> Strategy [a]
    evalList' t s as = sequence $ foldr f [] $ zip as [1..]
    where f (a, n) ss | n `mod` t == 0 = s (traceShow n a):ss
    | otherwise = s a:ss

    parList' :: Integer -> Strategy a -> Strategy [a]
    parList' t s = evalList' t (rparWith s)

    parMap' :: Integer -> Strategy b -> (a -> b) -> [a] -> [b]
    parMap' t s f xs = map f xs `using` parList' t s

    -- some work to do
    fib :: Integer -> Integer
    fib 0 = 1
    fib 1 = 1
    fib n = fib (n-1) + fib(n-2)

    main = do hSetBuffering stdout NoBuffering
    print $ sum (parMap' 1000 rseq (fib.(+20).(`mod` 5)) ([1..10000]::[Integer]))

    如果每个列表元素给出的工作包变小,您可以相应地调整 parListChunk。

    关于haskell - 跟踪 `map` 的进度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28016604/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com