我一直在尝试使用此功能并使用 iterate 和 takeWhile 进行小型实现。它不必使用这些功能,实际上我只是想把它变成一行。我可以看到其中的模式,但如果没有基本上制作相同的代码,我似乎无法利用它,只是使用迭代而不是递归。

fun2 :: Integer -> Integer
fun2 1 = 0
fun2 n
    | even n = n + fun2 (n `div` 2)
    | otherwise = fun2 (3 * n + 1)

任何帮助都会很棒。我已经为此苦苦挣扎了几个小时。
谢谢

最佳答案

如果你想用 iterate 做到这一点,关键是把它分成更小的逻辑部分:

  • 使用规则生成序列

    ak+1 = ak/2 如果 ak 是偶数

    ak+1 = 3ak+1 如果 ak 是奇数
  • 在 aj = 1 处停止序列(如果 collatz conjecture 为真,所有都这样做)。
  • 过滤掉路径上的偶数元素
  • 对它们求和

  • 那么这就变成了:
      f = sum . filter even . takeWhile (>1) . iterate (\n -> if even n then n `div` 2 else 3*n + 1)
    

    但是,我确实认为使用辅助函数会更清楚
      f = sum . filter even . takeWhile (>1) . iterate collatz
        where collatz n | even n    = n `div` 2
                        | otherwise = 3*n + 1
    

    这可能不会为您节省任何行,但会将您的递归转换为数据的生成。

    关于Haskell 迷你函数实现,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/14803593/

    10-13 03:09