putting it together

Discussion of Common Lisp
Post Reply
yuiop
Posts: 1
Joined: Tue Feb 08, 2011 11:16 am

putting it together

Post by yuiop » Tue Feb 08, 2011 11:46 am

Hi,


Code: Select all

(defun titlep (name)
  (member (first name) '(mr ms miss mrs)))

(setq male-first-names
      '(john kim richard fred george))

(setq female-first-names
      '(jane mary wanda barbara kim))

(defun malep (name)
  (and (member name male-first-names)
       (not (member name female-first-names))))

(defun femalep (name)
    (and (member name female-first-names)
    (not (member name male-first-names))))
The above codes are from the book "A Gentle Introduction to Symbolic Computation"
I have no problem running those line by line to the REPL but if i try to save it as one file and compile it, I would get errors.

Code: Select all

give-title.cl:4:1:
  warning: undefined variable: MALE-FIRST-NAMES

give-title.cl:7:1:
  warning: undefined variable: FEMALE-FIRST-NAMES

give-title.cl:11:8:
  warning: undefined variable: MALE-FIRST-NAMES

give-title.cl:12:13:
  warning: undefined variable: FEMALE-FIRST-NAMES

give-title.cl:15:10:
  warning: undefined variable: FEMALE-FIRST-NAMES

give-title.cl:16:10:
  warning: undefined variable: MALE-FIRST-NAMES

Compilation failed.
What am I doing wrong here?

I'm new to both programming and common lisp.

jstoddard
Posts: 20
Joined: Fri Jan 28, 2011 6:13 pm

Re: putting it together

Post by jstoddard » Tue Feb 08, 2011 5:22 pm

Just going to throw out my best guess at the problem (I'm new too, so I've got plenty potential for error here)...

setq sets a variable, but in this case the variables haven't been established/declared/whatever. You do this for global variables with defvar or defparameter, and for local variables w/ let.

For global variables it's normal to name them w/ asterisks, e.g. *male-first-names* instead of male-first-names, but in any case, you can try replacing "setq" with "defvar" and see if your program compiles better...

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: putting it together

Post by gugamilare » Wed Feb 09, 2011 3:28 am

jstoddard wrote:Just going to throw out my best guess at the problem (I'm new too, so I've got plenty potential for error here)...

setq sets a variable, but in this case the variables haven't been established/declared/whatever. You do this for global variables with defvar or defparameter, and for local variables w/ let.

For global variables it's normal to name them w/ asterisks, e.g. *male-first-names* instead of male-first-names, but in any case, you can try replacing "setq" with "defvar" and see if your program compiles better...
Yes, that is right. You should declare your global variables before using them, and change their values with setf or setq after they are defined.

JamesF
Posts: 98
Joined: Thu Jul 10, 2008 7:14 pm

Re: putting it together

Post by JamesF » Wed Feb 09, 2011 6:22 pm

Hi Yuiop,

Where you're using setq, you should be using either defvar or defparameter.
They both declare a special variable (like a global variable, basically), and in this case that's all you want. setq (or setf, more commonly) is for updating the variable's value afterwards, and you're not doing that here.

The difference between these is that defvar will only create the variable if it doesn't already exist, whereas defparameter will go right ahead and clobber an existing one if it happens to be in the way. This is mainly of importance when you're working within a session for an extended time, and want to make sure that if you change the definition it won't affect state that you're already working with like, say, changing the connection details of a database with which you're interacting. Alternatively, you may want to make sure it takes effect now, without having to exit the session and start again; sometimes you want one guarantee for some things and the other guarantee for others, both at the same time.


HTH,
James

vsedach
Posts: 8
Joined: Wed Dec 17, 2008 1:59 pm
Location: Montreal, QC, CA
Contact:

Re: putting it together

Post by vsedach » Thu Feb 10, 2011 4:04 pm

Looks like "A Gentle Introduction to Symbolic Computation" may need some errata. I don't see a list on the author's website.

edgar-rft
Posts: 226
Joined: Fri Aug 06, 2010 6:34 am
Location: Germany

Re: putting it together

Post by edgar-rft » Thu Feb 10, 2011 10:36 pm

Looking at the Touretzky book:
  • SETF is introduced in Chapter_5.3, page 138.
  • The code example from above (using SETF, not SETQ like above) is from Chapter_6.7, page 175.
  • DEFVAR is introduced in Chapter_14.10 "Compiling programs", page 417.
It's not really a miracle that an example from Chapter_6.7 produces an error on compilation of uninitialized variables if compiling programs is explained much later in Chapter_14.10, so the main lesson is: Do not try to do things you still haven't learned.

But the real problem is that the exact behaviour of SETQ and SETF on uninitialized variables is left "implementation dependent" and not clearly defined, see:
It's left to the implementation if compiling SETQ or SETF on undefined variables signals an error or not. Most implementations signal a warning and compile uninitialized variables as if they were declared with DEFVAR, but it's also allowed to signal an error and abort compilation.

A general rule of thumb is first to initialize variables with DEFVAR or DEFPARAMETER and only afterwards use SETQ or SETF to change the value if necessary. This should work with all implementations.

Post Reply