Exercise 3.3. Modify the make-account procedure so that it creates password-protected accounts. That is, make-account should take a symbol as an additional argument, as in
(define acc (make-account 100 'secret-password))
The resulting account object should process a request only if it is accompanied by the password with which the account was created, and should otherwise return a complaint:
((acc 'secret-password 'withdraw) 40)
60
((acc 'some-other-password 'deposit) 50)
"Incorrect password"
添加密码机制需要
- 另外定义一个过程 password-error
- 修改 make-account 和 dispatch 的接口
- dispatch 需要首先判断密码是否正确
(define (make-account balance password)
(define (withdraw amount)
(if (>= balance amount)
(begin (set! balance (- balance amount))
balance)
"Insufficient funds"))
(define (deposit amount)
(set! balance (+ balance amount))
balance)
(define (password-error dummy) "Incorrect password")
(define (dispatch pwd m)
(cond ((not (eq? pwd password)) password-error)
((eq? m 'withdraw) withdraw)
((eq? m 'deposit) deposit)
(else (error "Unknown request -- MAKE-ACCOUNT"
m))))
dispatch)
;;; tests begin
(load "../testframe.scm")
(let ((acc (make-account 100 'pwd)))
(assert= ((acc 'pwd 'deposit) 100) 200)
(assert= ((acc 'pwd 'withdraw) 200) 0)
(assertequal? ((acc 'pwd 'withdraw) 100) "Insufficient funds")
(assertequal? ((acc 'pwd1 'deposit) 100) "Incorrect password")
(assert= ((acc 'pwd 'deposit) 100) 100))
需要注意的是 password-error 过程需要一个参数占位,以便下面这样的调用不会出错:
((acc 'some-other-password 'deposit) 50)