Questions tagged [continuation-passing]

In functional programming, continuation-passing style (CPS) is a style of programming in which control is passed explicitly in the form of continuation function(s).

In CPS, in addition to receiving arguments as usual, each function also receives an additional function to be used as a continuation, so that instead of being returned as usual, a value is rather passed to this continuation function, as the function's final act.

Continuation functions are not expected to return in a normal sense, but rather return their values in the same manner, by further calling other continuation functions.

A computation either simply calls its continuation function, or constructs a new, more complex one, to express more complex patterns of computation, like recursion, or iteration.

Sometimes more than one continuation are used for each call, as e.g. with two continuations, one for a "successful" computation, another for a "failed" one.

Example:

nlog(n, x, onSuccess, onFailure) =            (* iterated logarithm *)
     onFailure(x)                      , if x <= 0 or n < 0
     onSuccess(x)                      , if n == 0
     onSucess(log(x))                  , if n == 1
     nlog(n-1, x, 
           x => onSuccess(log(x)),            (* new success continuation constructed *)
           onFailure                          (* same failure continuation *)
           )                           , otherwise
164 questions
157
votes
3 answers

What's the difference between a continuation and a callback?

I've been browsing all over the web in search of enlightenment about continuations, and it's mind boggling how the simplest of explanations can so utterly confound a JavaScript programmer like myself. This is especially true when most articles…
Aadit M Shah
  • 72,912
  • 30
  • 168
  • 299
31
votes
5 answers

How can two continuations cancel each other out?

I'm reading through Some Tricks for List Manipulation, and it contains the following: zipRev xs ys = foldr f id xs snd (ys,[]) where f x k c = k (\((y:ys),r) -> c (ys,(x,y):r)) What we can see here is that we have two continuations stacked…
27
votes
4 answers

continuation passing style vs monads

What are the differences between continuation passing style (cps) and monads.
Carlo V. Dango
  • 13,322
  • 16
  • 71
  • 114
26
votes
2 answers

Why continuation passing style

In The Scheme Programming Language by Kent Dybvig (4th edition) section 3.4, he describes very clearly what continuation passing style is. For the why he gives two reasons: pass more than one result to its continuation, because the procedure that…
Harry Spier
  • 1,395
  • 16
  • 30
21
votes
7 answers

Explain the continuation example on p.137 of The Little Schemer

The code in question is this: (define multirember&co (lambda (a lat col) (cond ((null? lat) (col (quote ()) (quote ()))) ((eq? (car lat) a) (multirember&co a (cdr lat) (lambda…
nweiler
  • 1,140
  • 1
  • 13
  • 23
21
votes
3 answers

How could the new async feature in c# 5.0 be implemented with call/cc?

I've been following the new announcement regarding the new async feature that will be in c# 5.0. I have a basic understanding of continuation passing style and of the transformation the new c# compiler makes to code like this snippet from Eric…
Gabe Moothart
  • 31,211
  • 14
  • 77
  • 99
17
votes
2 answers

Is continuation passing style any different to pipes?

I've been learning about continuation passing style, particularly the asynchronous version as implemented in javascript, where a function takes another function as a final argument and creates an asychronous call to it, passing the return value to…
Phil H
  • 19,928
  • 7
  • 68
  • 105
16
votes
1 answer

Continuation passing style representation of types

Suppose we have a monad, defined by return, (>>=) and the set of laws. There is a data type newtype C m a = C { unC ∷ forall r. (a → m r) → m r } also known as Codensity. C m a ≅ m a given that m is a Monad, i.e. we can write two functions to ∷…
Matvey Aksenov
  • 3,802
  • 3
  • 23
  • 45
15
votes
4 answers

The Little Schemer evens-only*&co

I'm having difficulty understanding what's going on with The Little Schemer's evens-only*&co example on page 145. Here's the code: (define evens-only*&co (lambda (l col) (cond ((null? l) (col '() 1 0)) ((atom? (car l)) (cond …
14
votes
1 answer

Can the continuation monad transformer be given an Alternative instance with some and many?

We can define the continuation monad transformer as data Cont r m a = Cont {run :: (a -> m r) -> m r} We can give Cont r m an Alternative instance if m is a member of Alternative via empty = Cont $ \f -> empty ca <|> cb = Cont $ \f -> run ca f <|>…
13
votes
3 answers

Is there a real-world applicability for the continuation monad outside of academic use?

(later visitors: two answers to this question both give excellent insight, if you are interested you should probably read them both, I could only except one as a limitation of SO) From all discussions I find online on the continuation monad they…
Abel
  • 56,041
  • 24
  • 146
  • 247
13
votes
1 answer

why do continuations avoid stackoverflow?

I've been trying to understand continuations / CPS and from what I can gather it builds up a delayed computation, once we get to the end of the list we invoke the final computation. What I don't understand is why CPS prevents stackoverflow when it…
dusio
  • 480
  • 5
  • 18
13
votes
2 answers

Why does the OCaml std lib have so many non-tail-recursive functions?

I have been rewriting many OCaml standard library functions to be tail-recursive lately. Given that this has entailed straight-forward CPS transformation, I am left puzzling over why the default versions are not written this way. As an example, in…
efrey
  • 399
  • 1
  • 12
12
votes
2 answers

What are the requirements to prefer CPS over algebraic data types?

I have little experience with algebraic data types, because I work in a language without native support. Usually one can use continuation passing style to get a remotely similar experience, but the handling of CPS encoded types is less…
12
votes
3 answers

Is there a way to chain functions like withCString?

Is there a way to chain functions like withCString? By that I mean any function that looks something like f :: Foo -> (CFoo -> IO a) -> IO a. For example, lets say there is a function cFunc :: CString -> CFoo -> CBar -> IO () Usualy, I would do…
1
2 3
10 11