2014-11-02 3 views
1

Я пытаюсь, чтобы полностью понять объекты и локальные состояния их переменныхМестное состояние переменной

Этот код, кажется, дают разные результаты по той же процедуре вызывается несколько раз, то есть локальные переменные изменения:

(define new-withdraw 
    (let ((balance 100)) 
    (lambda (amount) 
     (if (>= balance amount) 
      (begin (set! balance (- balance amount)) 
       balance) 
      "Insufficient funds")))) 

Для этого другого кода, он дает тот же результат, что означает, что он создает новую локальную переменную для каждого вызова процедуры:

(define (make-account) 
    (let ((balance 100)) 
    (define (withdraw amount) 
     (if (>= balance amount) 
      (begin (set! balance (- balance amount)) 
       balance) 
      "Insufficient funds")) 
    (define (deposit amount) 
     (set! balance (+ balance amount)) 
     balance) 
    (define (dispatch m) 
     (cond ((eq? m 'withdraw) withdraw) 
      ((eq? m 'deposit) deposit) 
      (else (error "Unknown request -- MAKE-ACCOUNT" 
         m)))) 
    dispatch)) 

Мои вопросы в Re:

  • Почему они ведут себя по-разному, несмотря на создание локальной переменной с помощью пусть?

  • Есть ли способ, чтобы второй код работал как первый, без прохождения balance в качестве параметра make-account?

Спасибо

ответ

2

тестирования кода 1:

> (new-withdraw 0) 
100 
> (new-withdraw 50) 
50 
> (new-withdraw 10) 
40 

тестирования кода 2:

> (define ac (make-account)) 
> ((ac 'withdraw) 0) 
100 
> ((ac 'withdraw) 50) 
50 
> ((ac 'withdraw) 10) 
40 

Так как коды держать их локальное состояние. Разница между кодом 1 и кодом 2 заключается в том, что код 1 работает только для одной учетной записи, тогда как код 2 «создает новую учетную запись» для каждого вызова - вызов процедуры возвращает процедуру диспетчеризации, которую необходимо связать с переменной, и затем используйте, как показано выше.

Поэтому создается впечатление, что местное государство потеряно; это не так, вы, вероятно, каждый раз создавали новую учетную запись.

+0

Ха, я вижу. когда я протестировал эту процедуру, я запустил '' (define acc make-account) (((acc) 'remove) 50) '', так что была определена новая локальная переменная каждый раз, когда '' acc'' был использован – user3450695