Reputation: 77
I have been confused about the following program for a long time. in fact, it's a exercise of SICP 3.2
;exercises 3.2
(define (make-monitored f)
(define (monitor count)
(define how-many-calls
count)
(define reset-count
(set! count 0))
(define (dispatch param)
(cond ((eq? param 'how-many-calls) how-many-calls)
((eq? param 'reset-count) reset-count)
(else (begin (set! count (+ count 1))
(f param)))))
dispatch
)
(monitor 0))
(define (square x) (* x x))
> (define s (make-monitored square))
> (s 10)
100
> (s 'how-many-calls)
0
>
my question is , why the output of "(s 'how-many-calls)" is 0 not 1? can I define a value dynamicly changed? (define how-many-calls count) I want the value of how-many-calls dynamic change when count changes.
Upvotes: 0
Views: 116
Reputation: 85853
The definition of how-many-calls
isn't what you want. It's being defined as a constant value:
(define (monitor count)
(define how-many-calls ; defines how-many-calls as the (initial)
count) ; value of count
This means that when you get into the first case of your cond
, you're always returning the same value, viz., the value of how-many-calls
, which is just the original value of count
, i.e., 0.
(define (dispatch param)
(cond ((eq? param 'how-many-calls) how-many-calls)
There's a similar problem with reset-count
:
(define reset-count ; defines reset-count as the value of
(set! count 0)) ; (set! count 0), which is probably void
((eq? param 'reset-count) reset-count) ; return the value of reset-count
As Chris Jester-Young's answer points out, you want to define how-many-calls
as procedures, and to call them from the cond
clauses.
Upvotes: 2
Reputation: 223023
You are missing some parentheses. Here's a fixed version of the code:
(define (make-monitored f)
(define (monitor count)
(define (how-many-calls)
count)
(define (reset-count)
(set! count 0))
(define (dispatch param)
(cond ((eq? param 'how-many-calls) (how-many-calls))
((eq? param 'reset-count) (reset-count))
(else (begin (set! count (+ count 1))
(f param)))))
dispatch)
(monitor 0))
Upvotes: 2