乐正

Actions speak louder than words.

Sicp-ex3-2

问题

在对应用程序做软件测试时,能够统计出在计算过程中某个给定的过程被调用的次数常常很有用处。请写出一个过程make-monitored,它以一个过程f作为输入,该过程本身有一个输入。make-monitored返回的结果是第三个过程,比如说mf,它将用一个内部计数器维持着自己被调用的次数。如果mf的输入是特殊符号has-many-call?,那么mf就返回内部计数器的值,如果输入的是特殊符号reset-count,那么mf就将计数器重新设置为0;对于任何其他输入,mf将返回过程f应用于这一输入的结果,并将内部的计数器加一。例如,我们可能以下面的方式做出过程sqrt的一个受监视的版本:

1
2
3
4
5
6
7
(define s (make-monitored sqrt))

(s 100)
10

(s 'how-many-calls)
1

解答

练习3.2 (ex3-2.scm) download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
(define (make-monitored f)
  (let ((counter 0))
    (define (reset)
      (set! counter 0)
      counter)
    (define (incr)
      (set! counter (+ counter 1)))
    (define (invoke arg)
      (incr)
      (f arg))
    (define (dispatch m)
      (cond ((eq? m 'how-many-calls?) counter)
            ((eq? m 'reset) (reset))
            (else (invoke m))))
    dispatch))

测试

1
2
3
4
5
6
7
8
9
10
11
12
13
14
(define s (make-monitored sqrt))
;Value: s

(s 100)
;Value: 10

(s 'how-many-calls?)
;Value: 1

(s 'reset)
;Value: 0

(s 'how-many-calls?)
;Value: 0

draft

« sicp-ex3-1 sicp-ex3-3 »

Comments