2010-12-12 9 views
2

先日、ChanLの出典を読んでいました。先物を実装するためのチャネルの使用例が含まれています。 DEFUNsはlike so、LET内で宣言された:LEF内のDEFUN - なぜですか?

(let ((some-var some-value)) 
    (defun foo() ... (reference some-var) ...) 
    (defun bar() ...)) 

、これはどのような目的を果たすのでしょうか?いくつかの機能が共有できる共通の価値を提供するだけで、カプセル化をきれいに保つことができますか?

答えて

6

あなたは既にあなたの質問に答えました:機能のグループに共有バインディングを提供し、カプセル化をきれいに保つこと。 http://letoverlambda.com/textmode.cl/guest/chap2.htmlから

簡単な例では:

(let ((direction 'down)) 
    (defun toggle-direction() 
    (setq direction 
      (if (eq direction 'up) 
       'down 
       'up)))) 
(toggle-direction) => UP 
(toggle-direction) => DOWN 
(toggle-direction) => UP 
(toggle-direction) => DOWN 

また、動作は方向に依存し、このクロージャ内の機能を追加することができます。

+2

。私はラムダを過ごすのコピーを購入しなければならない! –

2

これは単なるクロージャーです。ただ、歴史的な文脈[1]のために、

クロージャはアベルソンとサスマンの古典構造とコンピュータプログラムの解釈 が推進するプログラミング のスタイルでより顕著な役割を果たしています。クロージャは、ローカル状態の関数です。

(let ((counter 0)) 
    (defun new-id() (incf counter)) 
    (defun reset-id() (setq counter 0))) 

これら2つの関数はカウンタとして働く変数を共有する:この状態を使用する 最も簡単な方法は、次のような状況にあります。 最初のカウンタはカウンタの連続した値を返し、2番目の はカウンタを0にリセットします。 カウンタをグローバル変数にすることで同じことが実行できますが、この方法では の意図しない参照から保護されます。章では、いくつかの非常に興味深い読書になり、参照

Paul Graham - On lisp

関連する問題