monad的创造性使用

时间:2009-01-05 12:10:14

标签: haskell monads

我正在寻找monad的创造性用途来学习。我已经读过某个地方,在AI中已经使用了monad,但是作为monad新手,我没有看到如何。

请提供源代码和示例用法的链接。请不要standard monads

8 个答案:

答案 0 :(得分:30)

Phil Wadler撰写了many papers on monads,但首先阅读的内容非常有趣,任何程序员都可以访问;它被称为The essence of functional programming。本文包括源代码和样本用法。

我最喜欢的是probability monad;如果你能找到Sungwoo Park的博士论文,它有很多有趣的机器人示例代码。

答案 1 :(得分:16)

还有LogicT(回溯单子变换器,具有公平操作和修剪)。

它具有良好的AI搜索算法价值,因为它具有公平分离的结构,例如,可以轻松实现无限次成功的计算( interleaved )。

它的用法在ICFP'05论文Backtracking, Interleaving, and Terminating Monad Transformers

中有所描述

答案 2 :(得分:13)

您可以在博客A Neighborhood of Infinity中找到有趣且高级的monad。我可以注意到Vector Space Monad及其用于rational tangles描述的用法。不幸的是,我认为我不太了解这一点在这里解释它。

答案 3 :(得分:10)

我最喜欢的一个单子是Martin Escardo's search monad。它可以找到on hackage in infinite-search package

对于a类型的一组元素,它是“搜索函数”的monad,即(a -> Bool) -> Maybe a(在集合中查找与给定谓词匹配的元素)。

答案 4 :(得分:8)

monad的一个有趣用途是解析。 Parsec是标准示例。

答案 5 :(得分:8)

Harpy是一个用于运行时生成x86机器代码的软件包,它使用code generation monad。从描述:

  

这是一个组合的读者 - 状态 - 异常monad,它处理处理代码缓冲区,发送二进制数据,重定位等的所有细节。

     

模块Harpy.X86CodeGen中的所有代码生成函数都存在于此monad中,并使用其错误报告功能以及monad维护的​​内部状态。

     

库用户可以通过monad传递用户环境和用户状态。此状态独立于内部状态,可供更高级别的代码生成库用于跨代码生成操作维护自己的状态。

我发现这是一个特别有趣的例子,因为我认为这种模式并不罕见:我自己发明了一些非常相似的东西,根据从(股票)市场数据源收到的消息为我的应用程序生成一组内部消息。事实证明,这是一种非常舒适的方式,让一个框架跟踪各种“全局”事物,同时组成简单的操作,这些操作本身不会保持状态。

我更进一步了解了一个用户状态(我称之为“子状态”)的想法,它也可以通过monad传递:我有一个在monad运行期间切换和恢复状态的机制:

-- | Given a generator that uses different substate type, convert it
-- to a generator that runs with our substate type. As well as the
-- other-substate-type generator, the caller must provide an initial
-- substate for that generator and a function taking the final substate
-- of the generator and producing a new substate of our type. This
-- preserves all other (non-substate) parts of the master state touched
-- by the generator.
--
mgConvertSubstate :: MsgGen msg st' a -> st' -> (st' -> st) -> MsgGen msg st a

这用于组合子的子组,这些组合子在短时间内需要它们自己的状态。这些只运行状态,不知道调用它的生成器的状态(这有助于使事情更加模块化),但这保留了任何非用户特定的状态,例如生成的当前消息列表和当前的一组警告或错误,以及控制流程(即允许总中止向上流动)。

答案 6 :(得分:7)

阅读关于monad的系列文章,用于对概率和概率过程进行建模:http://www.randomhacks.net/articles/2007/03/03/smart-classification-with-haskell(按照上一个/下一个部分的链接)

答案 7 :(得分:5)

我想列出其他答案中尚未提及的几个单子。

枚举和加权搜索monad

The Omega monad可用于高效地遍历无限的结果列表。比较:

>>> take 10 $ liftM2 (,) [0..] [0..]
[(0,0),(0,1),(0,2),(0,3),(0,4),(0,5),(0,6),(0,7),(0,8),(0,9)]

>>> take 10 $ runOmega $ liftM2 (,) (each' [0..]) (each' [0..])
[(0,0),(0,1),(1,0),(0,2),(1,1),(2,0),(0,3),(1,2),(2,1),(3,0)]

使用更高级的WeightedSearch monad,还可以为计算分配权重,以便具有较低权重的计算结果首先出现在输出中。

累积错误monad

有用的These data type形成与Monad类似的Either,但能够累积错误。该软件包还基于These定义MonadChronicle class以及ChronicleT monad transformer