haskell - 如何在递归函数中使用 Control.Monad.Cont?
问题描述
我正在为这个问题提供一个答案,我想到了一个使用Cont
monad的想法。我对 Haskell 了解得不够多,无法解释为什么这个程序不起作用
import Control.Monad.Cont
fib1 n = runCont (slow n) id
where
slow 0 = return 0
slow 1 = return 1
slow n = do
a <- slow (n - 1)
b <- slow (n - 2)
return a + b
main = do
putStrLn $ show $ fib1 10
错误 -
main.hs:10:18: error:
• Occurs check: cannot construct the infinite type: a2 ~ m a2
• In the second argument of ‘(+)’, namely ‘b’
In a stmt of a 'do' block: return a + b
In the expression:
do a <- slow (n - 1)
b <- slow (n - 2)
return a + b
• Relevant bindings include
b :: a2 (bound at main.hs:9:7)
a :: a2 (bound at main.hs:8:7)
slow :: a1 -> m a2 (bound at main.hs:5:5)
|
10 | return a + b
|
但这对我来说没有意义。为什么我有a2
and m a2
?我期待a
并且b
是同一类型。
这让我很烦,因为相同的程序在 JavaScript 中运行良好。也许 Haskell 需要类型提示?
const runCont = m => k =>
m (k)
const _return = x =>
k => k (x)
const slow = n =>
n < 2
? _return (n)
: slow (n - 1) (a =>
slow (n - 2) (b =>
_return (a + b)))
const fib = n =>
runCont (slow(n)) (console.log)
fib (10) // 55
解决方案
return a + b
解析为(return a) + b
,而您想要return (a + b)
. 请记住,函数应用程序比任何中缀运算符绑定得更紧密。
(写成 也很常见return $ a + b
,相当于同一件事)
推荐阅读
- docker - docker挂载卷的奇怪分配所有者
- python - Python在2个脚本之间使用变量进行多处理
- css - 谁能指导我在这段代码中创建另一个菜单?
- c++ - 从 txt 文件中读取由字符分隔的元素
- python - 在 selenium 中实现复杂的 unicode emoji 字符
- ios - SwiftUI — Color.yellow 在 iOS 设备上呈现为棕色(但在模拟器中呈现为黄色)
- android - Android 生产 Google 和 Facebook 签名不起作用
- reactjs - 是否可以更改反应道具
- oracle12c - 复合外键是否可以引用复合主键并且所有值都不匹配(Oracle)?在同一张桌子上?
- android - React Native 中的 SSE