Advanced Scheme - PowerPoint PPT Presentation

1 / 22
About This Presentation
Title:

Advanced Scheme

Description:

(define countdown (lambda (n) (writeln 'This only appears once' ... Second statement in body of countdown. The second statement produces an infinite loop ... – PowerPoint PPT presentation

Number of Views:39
Avg rating:3.0/5.0
Slides: 23
Provided by: itha9
Learn more at: https://www.ithaca.edu
Category:

less

Transcript and Presenter's Notes

Title: Advanced Scheme


1
Advanced Scheme
  • Continuations

2
Continuations
  • continuations allow you to save a computation at
    any place in its execution.
  • In scheme, use the built-in function
    call-with-current-continuation
  • Can abbreviate as call/cc in most versions of
    scheme (including Dr Scheme)
  • Can think of a continuation as a bookmark into a
    computation

3
call/cc
  • Call/cc is a built-in function
  • Takes as an argument a procedure of one parameter
  • Call/cc calls the passed function and binds the
    continuation to the parameter of the function.
  • When the parameter of the procedure is used in
    its body, computation jumps to the continuation
    and passes the argument to that point of the
    continuation

4
example
  • In this example, call/cc is called after the 1
    computation is done
  • The continuation at this point is bound to k and
    passed to the lambda
  • k is used in the call (k 3)
  • At this point the continuation is executed, ie
    execution is restarted right after the ( 1 and
    the argument of k (ie 3) is passed as the result
    of the continuation.
  • In other words it ignores any computation that
    occurred after the continuation started, but
    before the continuation was applied.
  • ( 1 (call/cc
  • (lambda (k)
  • ( 2 (k 3)))))
  • 4
  • gt

5
example
The continuation captures the computation. In
this case it occurs right after the 1, so when
the continuation is used it will return its value
to the 1 computation.
  • ( 1 (call/cc
  • (lambda (k)
  • ( 2 (k 3)))))
  • 4
  • gt

6
example
  • ( 1 (call/cc
  • (lambda (k)
  • ( 2 (k 3)))))
  • 4
  • gt

7
Example 2
  • In this example, call/cc is called after the 1
    computation is done, but there is more
    computation (ie values) after the call/cc
    function
  • The continuation at the call/cc is bound to k and
    passed to the lambda
  • k is used in the call (k 3)
  • At this point the continuation is executed, ie
    execution is restarted right after the ( 1 and
    the argument of k (ie 3) is passed as the result
    of the continuation.
  • But there is more computation to be done after
    the call/cc, so the 4 and 10 are added to the
    result also!
  • ( 1 (call/cc
  • (lambda (k)
  • ( 2 (k 3)))) 4 10)
  • 18
  • gt

8
Example 2
The continuation captures the computation in the
middle. In this case it occurs right after the
1, but before the adding of 4 and 10.
  • ( 1 (call/cc
  • (lambda (k)
  • ( 2 (k 3)))) 4 10)
  • 18
  • gt

When k (the continuation) is called, we pick up
at the 1, pass in the argument of k (I.e., 3)
and then finish the computation (add 4 and 10)
9
Escaping Continuations
  • Continuations can be used to escape from
    computations
  • Can conceptualize as jumping out of a procedure

10
Escaping Continuations example
  • (define list-product
  • (lambda (s)
  • (letrec
  • ((multList
  • (lambda (s)
  • (if (null? s)
  • 1
  • ( (car s) (multList(cdr s)))
  • ))))
  • (multList s))
  • )
  • )
  • Works, but inefficient
  • What if have a long list and end item is 0?
  • Will return through the entire list and multiply
    each item by 0!

11
Escaping Continuations example
  • One solution tail recursion
  • Another solution continuation
  • (define list-product
  • (lambda (s)
  • (call/cc
  • (lambda (exit)
  • (letrec
  • ((multList
  • (lambda (s)
  • (if (null? s)
  • 1
  • (if ( (car s) 0) (exit 0)
  • ( (car s) (multList(cdr s)))
  • )))))
  • (multList s))
  • ))
  • ))

12
Escaping Continuations example 2
  • Find an element in a list
  • Use a built-in function for-each
  • return does not exist in scheme
  • (and yes, I know that we could use a recursive
    function instead)
  • (define find-item
  • (lambda (wanted? theList)
  • (for-each
  • (lambda (element)
  • (if (wanted? element)
  • (return element)))
  • theList)
  • f))
  • To call
  • (find-item (lambda (x) (equal? x 'a)) '(b c d a e
    f g))

This code wont run! The function return doesnt
exist!
How can we return?
13
Escaping Continuations example 2
  • Instead of return use a continuation
  • (define find-item
  • (lambda (wanted? theList)
  • (call/cc
  • (lambda (return)
  • (for-each
  • (lambda (element)
  • (if (wanted? element)
  • (return t)))
  • theList)
  • f))))

The return becomes a continuation
14
Escaping Continuations example 3deep recursion
  • adds a number to the product of a list of
    numbers
  • (define product
  • (lambda (n nums)
  • (let ((receiver
  • (lambda (exit-on-zero)
  • (letrec
  • ((product
  • (lambda (nums)
  • (cond
  • ((null? nums) 1)
  • ((number? (car nums))
  • (cond
  • ((zero? (car
    nums))(exit-on-zero 0))
  • (else ( (car nums)
  • (product (cdr
    nums))))))
  • (else ( (product (car
    nums))
  • (product (cdr
    nums))))))))
  • ( n (product nums))))))
  • (call/cc receiver))))

The exit-on-zero becomes a continuation
15
Saving Continuations
  • Can save a continuation and use it later
  • (define r f)
  • ( 1 (call/cc
  • (lambda (k)
  • (set! r k)
  • (k 3))))

4 gt (r 1) 2 gt (r 10) 11 gt (r 32) 33 gt ( 3 4 (r
20)) 21 gt
16
Background writeln
  • first must define writeln
  • (define writeln
  • (lambda lst
  • need a helper function to deal with the lst
    a recursive call to writeln
  • will place lst into another list
  • (letrec ((helper
  • (lambda (newlst)
  • (if (not (null? newlst))
  • (begin
  • (display (car newlst))
  • (display \space)
  • (helper (cdr newlst)))
  • (newline)))))
  • (helper lst))))

17
Looping with Continuations
  • loops with continuations
  • (define countdown
  • (lambda (n)
  • (writeln "This only appears once")
  • (let ((pair (message "Exit" (attempt (message
    "Enter" n)))))
  • (let ((v (car pair))
  • (returner (cadr pair)))
  • (writeln " The non-negative-number "
    v)
  • (if (positive? v)
  • (returner (list (sub1 v) returner))
  • (writeln "Blastoff!"))))))
  • (define message
  • (lambda (direction value)
  • (writeln " " direction "ing attempt with
    value " value)
  • value))
  • (define attempt
  • (lambda (n)
  • Welcome to DrScheme, version 209.
  • Language Graphical (MrEd, includes MzScheme).
  • (countdown 10)
  • This only appears once
  • Enter ing attempt with value 10
  • Exit ing attempt with value (10
    ltcontinuationgt)
  • The non-negative-number 10
  • Exit ing attempt with value (9
    ltcontinuationgt)
  • The non-negative-number 9
  • Exit ing attempt with value (8
    ltcontinuationgt)
  • The non-negative-number 8
  • Exit ing attempt with value (7
    ltcontinuationgt)
  • The non-negative-number 7
  • Exit ing attempt with value (6
    ltcontinuationgt)
  • The non-negative-number 6
  • Exit ing attempt with value (5
    ltcontinuationgt)
  • The non-negative-number 5
  • Exit ing attempt with value (4
    ltcontinuationgt)
  • The non-negative-number 4

18
Named let expressions
  • Background a named let
  • (define test
  • (lambda ()
  • (letrec ((countdown (lambda (i)
  • (if ( i 0) 'liftoff
  • (begin
  • (display i)
  • (newline)
  • (countdown (- i
    1)))))))
  • (countdown 10))))

(define test (lambda () (letrec
((countdown (lambda (i)
(if ( i 0) 'liftoff
(begin
(display i)
(newline)
(countdown (- i 1))))
))) (countdown 10))
))
19
Named let expressions
  • This is an infinite loop
  • (define test
  • (lambda ()
  • (letrec ((countdown (lambda (i)
  • (if ( i 0)
    'liftoff
  • (begin
  • (display i)
  • (newline)
  • (countdown
    (- i 1))))
  • (countdown 20))))
  • (countdown 10))
  • ))

(define test (lambda () (let countdown ((i
10)) (if ( i 0) 'liftoff (begin
(display i) (newline)
(countdown (- i 1)))) (countdown
20) )))
The second statement produces an infinite loop
20
Coroutines
  • (define hefty-computation
  • (lambda (do-other-stuff)
  • (letrec ((junk
  • (lambda (n)
  • (display "Hefty computation (a).
    ")
  • (display n)
  • (newline)
  • (set! do-other-stuff (call/cc
    do-other-stuff))
  • (display "Hefty computation (b).
    ")
  • (display n)
  • (newline)
  • (set! do-other-stuff (call/cc
    do-other-stuff))
  • (display "Hefty computation (c).
    ")
  • (display n)
  • (newline)
  • (set! do-other-stuff (call/cc
    do-other-stuff))
  • (if (gt n 0)
  • (junk (- n 1)))))
  • )

21
Coroutines
  • notationally displays a clock
  • uses a named let
  • (define superfluous-computation
  • (lambda (do-other-stuff)
  • (let loop()
  • (for-each (lambda (graphic)
  • (display graphic)
  • (newline)
  • (set! do-other-stuff (call/cc
    do-other-stuff)))
  • '("Straight-up" "Quarter after"
    "Half past" "Quarter till"))
  • (loop))))
  • (hefty-computation superfluous-computation)

22
Coroutines
  • notationally displays a clock
  • uses a letrec
  • (define superfluous-computation
  • (lambda (do-other-stuff)
  • (letrec
  • ((loop
  • (lambda ()
  • (for-each (lambda (graphic)
  • (display
    graphic)
  • (newline)
  • (set!
    do-other-stuff (call/cc do-other-stuff)))
  • '("Straight-up"
    "Quarter after" "Half past" "Quarter till"))
  • (loop) this causes infinite
    recursion in the local function
  • )))
  • (loop) the single statement in the
    letrec
  • )))
  • (hefty-computation superfluous-computation)
Write a Comment
User Comments (0)
About PowerShow.com