[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
free variable references in interpreter.
I don't believe there is anything in the Common Lisp book that
explicitly states that a Common Lisp implementation may not signal
errors in any situations not explicitly defined in the book to be
errors. On tbe other hand, I think there is at least an implicit
expectation that a purely computational section of a valid Common Lisp
program will execute without requiring the user to hit a "resume" key
every three seconds. I am not sure what we can say in the book about
this without unduly contraining experimentation with programming
environments and debugging tools.
Here is a set of thought experiments about a LISP system. Question: in
each case, is it or is is not consistent with the letter and/or the
spirit of Common Lisp? There are two subcases for each experiment,
according to whether the interpreter or compiler is involved. I will
use the noun "system" to refer to either the interpreter of the
compiler, and I will use "warning" to mean any action that draws the
user's attention to a message (and that may or may not require explicit
user action before continuing with the computation). Some of these
examples are intentionally outlandish.
(1) You refer to a function without declaring it first, and the system
gives you a warning. (Note that I said "declaring", not "defining".
Consider the compiler especially.)
(2) You refer to a special variable without declaring it, and the system
gives you a warning.
(3) You write "(+ x (cons y z))" and the system warns you that CONS
cannot produce (or has not produced) a value that is valid as an
argument to +.
(4) You write
(COND ((ATOM X) 'A) (T 'C) ((BAZ X) 'D))
and the system warns you that the last COND clause is unreachable.
(5) You write
(COND ((ATOM X) 'A) ((CONSP X) 'C) ((BAZ X) 'D))
and the system warns you that the last COND clause is unreachable.
(6) You write
(MULTIPLE-VALUE-BIND (A B C) (FLOOR X Y) ...)
and the system warns you that FLOOR returns only two values.
(7) You use several GO's in a PROG, and the system warns you that this
code will probably be very hard to maintain.
(8) You write
(DEFUN FIB (N)
(COND ((<= N 1) 1)) ;Note parenthesis error!
(T (+ (FIB (- N 1)) (FIB (- N 2)))))
and the system warns you that your code is not properly indented.
(9) You write
(DEFUN FIB (N)
(COND ((<= N 1) 1)
(T (+ (FIB (- N 1))
(FIB (- N 2))))))
and the system warns you that your code is not properly indented.
(10) You write a DO loop, and the system warns you that it could have
been expressed more simply and efficiently by using a call to RASSOC
with the :TEST-NOT and :KEY options.
(11) You write two nested DO loops, and the system warns you that the
SORT primitive is much better than the bubble sort that you wrote.
(12) You write
(DEFUN FIB (N) (IF (ZEROP N) 1 (* N (FIB (- N 1)))))
and the system warns you that your function FIB is computing factorials
and not Fibonacci numbers.
Is there some generalization we can derive from these thought
experiments, or others, that is worth putting in the book?
--Guy