Lisp, part 1

Last modified: "July 3, 1996 17:00:18 by matt"

Chapter 2 of Graham's ANSI Common Lisp ======================================================

TERMS:

toplevel (listener) operator and arguments: (+ 1 2) expressions: atoms or lists. 2, (+ 2 3)

EVALUATION

read - eval - print evaluation: 1. eval args (each an expression) left to right 2. pass resulting vals of args to operator and evaluate 3. "return" value of op Note that linefeeds are ignored by lisp. They serve only to make the code more readable. almost all lisp ops are functions (i.e., return a value) the QUOTE operator (the apostrophe) suspends evaluation of the next expression. symbols lisp programs are lists!

LIST OPERATORS

cons, car,cdr,nth,first,listp,consp, list All lists are comprised of a sequence of cons cells. Reading Lisp -- indentation and parentheses. Should be handled by your editor. Commercial lisp systems provide such editors. Emacs is one of the best, and is free. See the notes on the class Web pages.

VARIABLES

ASSIGNMENT

setq, setf pointers (setf (car x) 'a) Pointers are ubiquitous and implicit in Lisp, unlike most other programming languages, such as C. This leads to real flexibility in using the language. On the other hand, it also creates the need for garbage collection, because the user is not responsible for dynamic memory management. (I.e., no MALLOC or FREE in Lisp.)

FUNCTIONAL PROGRAMMING --

No globals, just give parms. Easy to experiment, because there are no side effects. Therefore, if a function/procedure works correctly in one instance, it should work correctly in all.

FUNCTIONS as OBJECTS

lambda expressions.

TYPES --

hah! No need for those in lisp, though their use does increase the efficiency of "compiled" lisp code.

PREDICATES

(atom 'a) (atom '( 1 2 3)) (listp '(1 2 3)) (atom nil) = (listp nil) = (null nil) CONSP == LISTP except for NIL (equal '(a b c) (list 'a 'b 'c)) There are other equality predicates, but EQUAL is most general. True if two things print the same. zerop, oddp, <, <=, != (typep 6 'number) (member 'b '(a b c)) ;; Doesn't just return T, since any non-NIL connotes true, and this is more informative. (member 'b '(a (b) c)) SEE APPENDIX D for more predicates

CONDITIONALS

if [] (cond ((listp x) (car x))) COND is a function, returning val of 1st term evaling to nonNIL. Similar to C's CASE statement. (defun car-atomp (x) (cond ((listp x) (atom (car x)) (t nil))) ; If this is omitted, still returns NIL (by def of COND) but this ; is more clear-cut. (cond ((= x 5) (setq z 3)) (t (setq z 4))) is completely equivalent to (if (= x 5) (setq z 3) (setq z 4))

LOGICAL OPERATORS

not and or

AND & OR as flow-of-control.

Evals left to right, stopping ASAP. (or (= x 4) (not (numberp x)) (setq x 5)) is functionally equivalent to: (if (and (not (= x 4)) (numberp x)) (setq x 5) t) (and (setq x 4) (not (numberp x)) (setq x 5))

LISP IS LEXICALLY SCOPED:

Understanding symbols vs. parameters/variables Symbols are statically bound. I.e., bound at definition, not at reference. > (defun wow (x) (setq x 5) (bow) (print x)) WOW > (defun bow () (setq x (* 2 x))) ;; x is a FREE variable, here, at definition time. BOW > (wow 2) >>Error: The symbol X has no global value SYMBOL-VALUE: Required arg 0 (S): X > (setq x 4) ; defines x at top level (i.e., globally) 4 > (wow 2) 5 5 > x 8 > (wow 2) 5 5 > x 16 >

Lisp uses lexical (aka static) scoping.

Dynamic scoping is possible, but what would be some problems with dynamic scoping? Debugging would be very difficult; simple examination of the program text would be insufficient to locate bugs. The program would have to be debugged during execution so that the programmer could examine the program stack. The Original Lisp used dynamic scoping. **DANGER, special variables ahead....*** > (defun wow (x) (declare (special x)) (setq x 5) (bow) (print x)) ;; Because WOW's X is "special", references to symbol x within the time that WOW ;; is executing will refer to the x defined in WOW's scope. In effect, WOW's x ;; "intercepts" references to "global" variable x. > (wow 2) 10 10 ;; Notice that the value of the "toplevel" x has not changed.... > x 16 >