0% found this document useful (0 votes)
239 views

10

The document discusses recursion and lazy evaluation in CS320. It provides details about a midterm exam on March 28th and answers questions about why we learn recursion and how recursion is implemented in the RCFAE programming language. Specifically, it describes how the RCFAE interpreter uses boxes and substitution to recursively evaluate expressions by lazily evaluating named functions.
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
239 views

10

The document discusses recursion and lazy evaluation in CS320. It provides details about a midterm exam on March 28th and answers questions about why we learn recursion and how recursion is implemented in the RCFAE programming language. Specifically, it describes how the RCFAE interpreter uses boxes and substitution to recursively evaluate expressions by lazily evaluating named functions.
Copyright
© Attribution Non-Commercial (BY-NC)
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 40

CS320:

Recursion and Lazy Evaluation


Sukyoung Ryu
March 12, 2012

CS320: Recursion and Lazy Evaluation

Midterm

March 28th Wednesday 11AM1PM

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion?

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion? 1 (n 1)! n 0 1 F n1 + Fn2 if n = 0 if n > 0 if n = 0 if n = 1 if n > 1

n! =

Fn =

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way?

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way?
Denition: a method where the solution to a problem depends on solutions to smaller instances of the same problem.a > Examples:
factorial(n) = if n = 0 then 1 else factorial(n-1) * n fibonacci(n) = if n = 0 then 1 else if n = 1 then 1 else fibonacci(n-1) + fibonacci(n-2)
> >

Interpreter: Dene a small language with recursion and implement its interpreter to see how it actually works.

L. Graham, Donald E. Knuth, and Oren Patashnik (1990). Concrete Mathematics. Chapter 1: Recurrent Problems.

a Ronald

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way? > Because DrRacket does not support recursion?

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way? > Because DrRacket does not support recursion?
; interp : AE -> number (define (interp an-ae) (type-case AE an-ae [num (n) n] [add (l r) (+ (interp l) (interp r))] [sub (l r) (- (interp l) (interp r))]))

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way? > Why not just use recursion supported by DrRacket? Why bother use dummy values for functions?

CS320: Recursion and Lazy Evaluation

Questions and Answers


Why do we learn recursion in this way? > Why not just use recursion supported by DrRacket? Why bother use dummy values for functions? > DrRacket denes recursive functions by define and RCFAE denes recursive functions by rec. > DrRacket looks up recursive functions from its internal symbol table and RCFAE looks up recursive functions from DefrdSub.

CS320: Recursion and Lazy Evaluation

RCFAE: Concrete Syntax


<RCFAE> ::= <num> | {+ <RCFAE> <RCFAE>} | {- <RCFAE> <RCFAE>} | <id> | {fun {<id>} <RCFAE>} | {<RCFAE> <RCFAE>} | {if0 <RCFAE> <RCFAE> <RCFAE>} | {rec {<id> <RCFAE>} <RCFAE>}

10

CS320: Recursion and Lazy Evaluation

RCFAE: Abstract Syntax


(define-type RCFAE [num (n number?)] [add (lhs RCFAE?) (rhs RCFAE?)] [sub (lhs RCFAE?) (rhs RCFAE?)] [id (name symbol?)] [fun (param symbol?) (body RCFAE?)] [app (fun-expr RCFAE?) (arg-expr RCFAE?)] [if0 (test-expr RCFAE?) (then-expr RCFAE?) (else-expr RCFAE?)] [rec (name symbol?) (named-expr RCFAE?) (body RCFAE?)])

11

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae [num (n) (numV n)] [add (l r) (num+ (interp l ds) (interp r ds))] [sub (l r) (num- (interp l ds) (interp r ds))] [id (name) (lookup name ds)] [fun (param body-expr) (closureV param body-expr ds)] [app (f a) (local [(define ftn (interp f ds))] (interp (closureV-body ftn) (aSub (closureV-param ftn) (interp a ds) (closureV-ds ftn))))] [if0 (c t e) (if (numzero? (interp c ds)) (interp t ds) (interp e ds))] [rec (bound-id named-expr body-expr) ...]))

12

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae ... [rec (bound-id named-expr body-expr) ...]))

13

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae ... [rec (bound-id named-expr body-expr) ... (interp named-expr ds) ... (interp body-expr ds) ...]))

14

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae ... [rec (bound-id named-expr body-expr) (local [(define new-ds (aRecSub bound-id ... ds))] ... (interp named-expr new-ds) ... (interp body-expr new-ds) ...)]))

15

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae ... [rec (bound-id named-expr body-expr) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub bound-id value-holder ds))] ... (interp named-expr new-ds) ... (interp body-expr new-ds) ...]))

16

CS320: Recursion and Lazy Evaluation

RCFAE: Interpreter
; interp : RCFAE DefrdSub -> RCFAE-Value (define (interp rcfae ds) (type-case RCFAE rcfae ... [rec (bound-id named-expr body-expr) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub bound-id value-holder ds))] (begin (set-box! value-holder (interp named-expr new-ds)) (interp body-expr new-ds)))]))

17

CS320: Recursion and Lazy Evaluation

RCFAE: DefrdSub
(define-type DefrdSub [mtSub] [aSub (name symbol?) (value RCFAE-Value?) (ds DefrdSub?)] [aRecSub (name symbol?) (value-box (box/c RCFAE-Value?)) (ds DefrdSub?)]) (define-type RCFAE-Value [numV (n number?)] [closureV (param Symbol?) (body RCFAE?) (ds DefrdSub?)])

18

CS320: Recursion and Lazy Evaluation

RCFAE: Lookup
; lookup : symbol DefrdSub -> num (define (lookup name ds) (type-case DefrdSub ds [mtSub () (error lookup "free variable")] [aSub (sub-name val rest-ds) (if (symbol=? sub-name name) val (lookup name rest-ds))] [aRecSub (sub-name val-box rest-ds) (if (symbol=? sub-name name) (unbox val-box) (lookup name rest-ds))]))

19

CS320: Recursion and Lazy Evaluation

Boxes in DrScheme
A box is like a single-element vector, normally used as minimal mutable storage. http://docs.racket-lang.org/reference/boxes.html box:
(define value-holder (box (numV 42))) (set-box! value-holder (interp named-expr new-ds))

set-box!: unbox: box/c:

(unbox val-box) (value-box (box/c RCFAE-Value?))

20

CS320: Recursion and Lazy Evaluation

Example Run!

(run "{rec {count {fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}} {count 8}}" (mtSub))

21

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (run "{rec {count {fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}} {count 8}}" (mtSub))

22

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (run "{rec {count {fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}} {count 8}}" (mtSub)) f fun-expr body value-holder new-ds = = = = =
23

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (run "{rec {count {fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}} {count 8}}" (mtSub)) f fun-expr body value-holder new-ds = = = = = "count" "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" "{count 8}" [numV 42] (aRecSub count value-holder (mtSub))
24

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (interp fun-expr new-ds) fun-expr body value-holder new-ds = = = = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" "{count 8}" [numV 42] (aRecSub count value-holder (mtSub))

25

CS320: Recursion and Lazy Evaluation

Example Run!

[fun (param body-expr) (closureV param body-expr ds)] (interp fun-expr new-ds) fun-expr body value-holder new-ds = = = = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" "{count 8}" [numV 42] (aRecSub count value-holder (mtSub))

26

CS320: Recursion and Lazy Evaluation

Example Run!

[fun (param body-expr) (closureV param body-expr ds)] (interp fun-expr new-ds) fun-expr = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" body = "{count 8}" value-holder = [numV 42] new-ds = (aRecSub count value-holder (mtSub)) (interp fun-expr new-ds) = (closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)

27

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (interp fun-expr new-ds) fun-expr = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" body = "{count 8}" value-holder = [numV 42] new-ds = (aRecSub count value-holder (mtSub)) (interp fun-expr new-ds) = (closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)

28

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (set-box! value-holder (interp fun-expr new-ds)) fun-expr = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" body = "{count 8}" value-holder = [numV 42] new-ds = (aRecSub count value-holder (mtSub)) (interp fun-expr new-ds) = (closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)

29

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (set-box! value-holder (interp fun-expr new-ds)) fun-expr = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" body = "{count 8}" value-holder = [(closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)] new-ds = (aRecSub count value-holder (mtSub)) (interp fun-expr new-ds) = (closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)

30

CS320: Recursion and Lazy Evaluation

Example Run!
[rec (f fun-expr body) (local [(define value-holder (box (numV 42))) (define new-ds (aRecSub f value-holder ds))] (begin (set-box! value-holder (interp fun-expr new-ds)) (interp body new-ds)))] (interp body new-ds) fun-expr = "{fun {n} {if0 n 0 {+ 1 {count {- n 1}}}}}" body = "{count 8}" value-holder = [(closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)] new-ds = (aRecSub count value-holder (mtSub)) (interp fun-expr new-ds) = (closureV n "{if0 n 0 {+ 1 {count {- n 1}}}}" new-ds)

31

CS320: Recursion and Lazy Evaluation

Lazy Evaluation

32

CS320: Recursion and Lazy Evaluation

Scheme vs. Algebra


In Scheme, we have a specic order for evaluating subexpressions: (+ (* 4 3) (- 8 7)) (+ 12 (- 8 7)) (+ 12 1) In Algebra, order does not matter: (4 3) + (8 7) 12 + (8 7) 12 + 1 or: (4 3) + (8 7) (4 3) + 1 12 + 1

33

CS320: Recursion and Lazy Evaluation

Algebraic Shortcuts
In Algebra, if we see: f (x, y ) = x g (z ) = . . . f (17, g (g (g (g (g (18)))))) then we can go straight to: 17 because the result of all the g calls will not be used.

34

CS320: Recursion and Lazy Evaluation

Lazy Evaluation
Languages like Scheme, Java, and C are called eager > An expression is evaluated when it is encountered Languages that avoid unnecessary work are called lazy > An expression is evaluated only if its result is needed

35

CS320: Recursion and Lazy Evaluation

LFAE = Lazy FAE


<LFAE> ::= | | | | | <num> {+ <LFAE> <LFAE>} {- <LFAE> <LFAE>} <id> {fun {<id>} <LFAE>} {<LFAE> <LFAE>}

36

CS320: Recursion and Lazy Evaluation

LFAE = Lazy FAE


<LFAE> ::= | | | | | <num> {+ <LFAE> <LFAE>} {- <LFAE> <LFAE>} <id> {fun {<id>} <LFAE>} {<LFAE> <LFAE>}

{{fun {x} 0} {+ 1 {fun {y} 2}}} {{fun {x} x} {+ 1 {fun {y} 2}}}

37

CS320: Recursion and Lazy Evaluation

LFAE = Lazy FAE


<LFAE> ::= | | | | | <num> {+ <LFAE> <LFAE>} {- <LFAE> <LFAE>} <id> {fun {<id>} <LFAE>} {<LFAE> <LFAE>}

{{fun {x} 0} {+ 1 {fun {y} 2}}} 0 {{fun {x} x} {+ 1 {fun {y} 2}}} error

38

Sukyoung Ryu
[email protected] http://plrg.kaist.ac.kr

You might also like