haskell - 解决狮子、狼和山羊的问题

标签 haskell

我正在尝试解决发现的狮狼和山羊问题 here

-- Lions Wolves Goats
-- Lion -> Wolf -> Goat :: -1, -1, +1
-- Lion -> Goat -> Wolf :: -1, +1, -1
-- Wolf -> Goat -> Lion :: +1, -1, -1
--                      -------------
--                      :: -1, -1, -1

这就是我的解决方案:

eat :: (Int, Int, Int) -> (Int, Int, Int)
eat (lions, wolves, goats) = eat (lions - 1, wolves - 1, goats - 1)
eat (0, wolves, goats) = eat (1, wolves - 1, goats - 1)
eat (lions, 0, goats) = eat (lions - 1, 1, goats - 1)
eat (lions, wolves, 0) = eat (lions - 1, wolves - 1, 1)
eat (0, 0, goats) = (0, 0, goats)

此代码可以编译,但代码会永远挂起。我很确定我错过了一场比赛,但我不知道是什么。请让我知道如何正确解决这个问题。

最佳答案

模式是从上到下、从左到右读取的。因此,您的第一个模式与所有其他模式相匹配。重新排序:

eat :: (Int, Int, Int) -> (Int, Int, Int)
eat (0     , 0      , goats) =     (0         , 0          , goats    )
eat (0     , wolves , goats) = eat (1         , wolves - 1 , goats - 1)
eat (lions , 0      , goats) = eat (lions - 1 , 1          , goats - 1)
eat (lions , wolves , 0)     = eat (lions - 1 , wolves - 1 , 1        )
eat (lions , wolves , goats) = eat (lions - 1 , wolves - 1 , goats - 1)

请注意,这假设所有值最初都是正数。如果其中之一为负,您仍然会出现循环。另请注意,您错过了其他“稳定”状态,并且您对狮子、狼和山羊的非零群的逻辑已关闭。如果有山羊和狼,狮子可能会吃掉它们中的任何一个。此外,狼可能会先于狮子吃掉山羊。

这就是非决定论发挥作用的部分。

关于haskell - 解决狮子、狼和山羊的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36097043/

相关文章:

haskell - 格式化长模式匹配

Haskell:如何将多个实例放在同一个模块中?

haskell - 从列表中删除 n 个元素

haskell - Pandoc 在 GHC 7.8.2 上编译失败

list - 递归定义一元随机数列表 : most idiomatic Haskell and analogous to pure code

algorithm - 纯 Knuth/Fisher-Yates 在 haskell 中洗牌

testing - 为什么 QuickCheck 放弃了?

haskell - 如何解决 Haskell 类型错误

使用组合映射的 Haskell 多态递归会导致无限类型错误

haskell - Haskell/GHCI 中的别名