Prev Up Next

Local variables can be introduced without explicitly creating a procedure. The special form let introduces a list of local variables for use within its body:

(let ((x 1)
      (y 2)
      (z 3))
  (list x y z))
=> (1 2 3)

As with lambda, within the let-body, the local x (bound to 1) shadows the global x (which is bound to 20).

The local variable initializations -- x to 1; y to 2; z to 3 -- are not considered part of the let body. Therefore, a reference to x in the initialization will refer to the global, not the local x:

(let ((x 1)
      (y x))
  (+ x y))
=> 21

This is because x is bound to 1, and y is bound to the global x, which is 20.

Sometimes, it is convenient to have let's list of lexical variables be introduced in sequence, so that the initialization of a later variable occurs in the lexical scope of earlier variables. The form let* does this:

(let* ((x 1)
       (y x))
  (+ x y))
=> 2

The x in y's initialization refers to the x just above. The example is entirely equivalent to -- and is in fact intended to be a convenient abbreviation for -- the following program with nested lets:

(let ((x 1))
  (let ((y x))
    (+ x y)))
=> 2

The values bound to lexical variables can be procedures:

(let ((cons (lambda (x y) (+ x y))))
  (cons 1 2))
=> 3

Inside this let body, the lexical variable cons adds its arguments. Outside, cons continues to create dotted pairs.

Prev Up Next

Log in or register to write something here or to contact authors.