gpt4 book ai didi

haskell - 我应该更喜欢 MonadUnliftIO 还是 MonadMask 来进行类似功能的括号?

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

我目前正在构建一个新的 API,它目前提供的功能之一是:

inSpan :: Tracer -> Text -> IO a -> IO a

我正在寻找移动 Tracer进入一个单子(monad),给我一个更像是的签名
inSpan :: MonadTracer m => Text -> m a -> m a 
inSpan的执行使用 bracket ,这意味着我有两个主要选择:
class MonadUnliftIO m => MonadTracer m

或者
class MonadMask m => MonadTracer m

但我应该更喜欢哪个?请注意,我可以控制我提到的所有类型,这让我稍微倾向于 MonadMask因为它不强制执行 IO在底部(也就是说,我们可能有一个纯 MonadTracer 实例)。

还有什么我应该考虑的吗?

最佳答案

让我们首先列出选项(在此过程中重复您的一些问题):

  • MonadMask来自 exceptions图书馆。这可以在各种单子(monad)和转换器上工作,并且不需要基础单子(monad)是 IO .
  • MonadUnliftIO来自 unliftio-core (或 unliftio )库。此库仅适用于具有 IO 的单子(monad)在它们的基础上,并且在某种程度上与 ReaderT env IO 同构.
  • MonadBaseControl来自 monad-control图书馆。该库需要 IO在基地,但将允许非 ReaderT。

  • 现在是权衡。 MonadUnliftIO是最新加入的竞争者,并且具有最不发达的库支持。这意味着,除了单子(monad)可以是实例的限制之外,许多好的实例还没有被编写出来。

    重要的问题是:为什么 MonadUnliftIO围绕 ReaderT 提出这个看似任意的要求- 类似的东西?这是为了防止丢失一元状态的问题。例如, bracket_ (put 1) (put 2) (put 3) 的语义不是很清楚,因此 MonadUnliftIO不允许 StateT实例。
    MonadBaseControl放松 ReaderT限制并具有更广泛的库支持。它在内部也被认为比其他两个更复杂,但是对于您的用法来说,这并不重要。它允许你在上面提到的一元状态中犯错误。如果您在使用时小心,这无关紧要。
    MonadMask允许完全纯变压器堆栈。我认为围绕在纯堆栈中建模异步异常的有用性有一个很好的论据,但我理解这种方法是人们有时想要做的事情。作为获得更多实例的交换,您仍然有围绕单子(monad)状态的限制,以及无法解除一些 IO控制操作,例如 timeoutforkIO .

    我的建议:
  • 如果你想匹配当今大多数人的做事方式,最好选择MonadMask。 ,这是最常用的解决方案。
  • 如果你想要那个目标,但你还需要做 timeoutwithMVar什么的,使用MonadBaseControl .
  • 如果你知道有一组特定的 monad 需要兼容,并且希望编译时保证你的代码相对于 monadic 状态的正确性,请使用 MonadUnliftIO .
  • 关于haskell - 我应该更喜欢 MonadUnliftIO 还是 MonadMask 来进行类似功能的括号?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46425062/

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