gpt4 book ai didi

haskell - 在 Haskell 中执行一系列操作时的异常处理

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

这是我希望将错误处理纳入其中的代码要点。

worldHandler :: ProcessState -> JobCount -> IO ()
worldHandler world jCount = do
putStrLn "Entered worldHandler"
jcount <- takeMVar jCount
if jcount > 0
then incrementThenDone jcount
else doJobProcessing jcount
where incrementThenDone jcount = do
putMVar jCount (jcount+1)


doJobProcessing jcount = do
putMVar jCount (jcount+1)
preProcess world
initiateJob world
makeChart world

这是主要

main :: IO ()
main = do
world <- (newEmptyMVar :: IO ProcessState)
jCount <- (newMVar 0 :: IO JobCount)
installHandler userDefinedSignal1 (Catch $ worldHandler world jCount) Nothing
forever (threadDelay 10000)

函数preProcessinitiateJobmakeChart是我需要的地方关心错误。这个想法是,如果这些函数中的任何一个失败,我递减 jCount 并调用 logError。然后,如果jCount > 0,则再次启动相同的三个函数。如果jCount == 0,则继续等待下一个信号。

每个函数都会启动另一个进程,readProcessWithExitCode 看起来像我想要的。然后我将使用退出代码以确定成功或失败。

我的一个想法是制作一个[preProcess、initiateJob、makeChart]。然后我将函数 jobProcessor 映射到这个列表上。如果其中之一函数从它们调用的程序中收到失败,我可以生成一个执行,map 将停止在列表上映射。

这是一个合理的方法吗?

关于如何解决这个问题的一般想法以及出现的任何问题谨记将不胜感激。

编辑:由于提出的第一个问题,我重新评估了我的解释,并指出它在一些重要方面不完整。我认为填补了空白。如果没有,请告诉我。

最佳答案

让我们先看看这个序列,暂时把计数放在一边。

preProcess world
initiateJob world
makeChart world

作为一个顶级函数,它看起来像

doJobProcessing :: ProcessState -> IO ()
doJobProcessing world = do
preProcess world
initiateJob world
makeChart world

。如果其中任何一个失败,我们希望中断该执行流程,并(可能)重新启动。

人们可以使用 Haskell 异常,也可以不使用。让我们首先看一个没有异常的解决方案,因为它也可以在非 IO 代码中工作。我不知道你的类型实际上是什么,所以让我们假设它们都是

preProcess, initiateJob, makeChart :: ProcessState -> IO ExitCode

现在这是一个极其丑陋的明显方法(总是一个好的开始)

doJobProcessing :: ProcessState -> IO ()
doJobProcessing world = do
preProcessStatus <- preProcess world
if preProcessStatus /= ExitSuccess
then jobFail world
else do
initiateJobStatus <- initiateJob world
if initiateJobStatus /= ExitSuccess
then jobFail world
else do
makeChartStatus <- makeChart world
if makeChartStatus /= ExitSuccess
then jobFail world
else return () ---success!!!

jobFail :: ProcessState -> IO ()
jobFail world = do
--some test involving jCount
if --test says to try again
then do
--inc/dec jCount
doJobProcessing world
else do
-- nothing; we give up
return ()

这符合您的要求吗? (如果 makeChart 失败,它会从 preProcess 的头开始重试。)如果确实如此,那么我将展示如何使用纯 Haskell 抽象和/或异常来简化它。 (如果您希望每个 preProcess、initiateJob 和 makeChart 仅重新启动自身,我将展示一种方法来实现这一点。)

关于haskell - 在 Haskell 中执行一系列操作时的异常处理,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7395356/

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