将Scheme调用/ cc转换为Haskell callCC

zab*_*kar 6 scheme continuations haskell

让我们考虑打破一个非终止的折叠:

(call/cc (lambda (folded)
  (stream-fold
    (lambda (acc v)
      (if (< v 5)
        (cons v acc)
        (folded acc)))
    '()
    (in-naturals 0))))
; returns '(4 3 2 1 0)
Run Code Online (Sandbox Code Playgroud)

Haskell相当于上面的代码

callCC $ \folded -> foldl (\acc v -> if v < 5 then v:acc else folded acc) [] [0..]
Run Code Online (Sandbox Code Playgroud)

此代码无法编译并抱怨无法在表达式折叠acc中构造无限类型.我已经知道如何在像Y组合器这样的情况下消除这种错误,但是同样的方法似乎在这里不起作用.这种情况的正确方法是什么?

goi*_*ain 6

是的; 作为j.亚伯拉罕森说,

import Control.Monad.Trans.Cont
import Control.Monad

bar :: Cont r [Int]
bar = callCC $ \folded ->
    foldM (\acc v -> do
        when (v >= 5) $ folded acc
        return $ v : acc) [] [0..]

thing = runCont bar id
Run Code Online (Sandbox Code Playgroud)

作品.