Monthly Archives: July 2014

The less-familiar parts of Lisp for beginners — slot-boundp

Over the next few articles, we’ll be discussing functions related to slots in an instance.  When a class is defined, its definition establishes the slots associated with that class, either directly or through inheritance.  Shared slots (static members, in the language of C++) are created immediately upon definition, but local slots (non-static members in C++) are not manifested before instances of the object are created.  A local slot within a particular instance can be bound or unbound.  It is bound by assigning a value to it, either by :initform, :initarg, or direct assignment through accessors or the application of setf acting on the slot-value function.  If none of those actions has taken place on a local slot in a particular instance, the local slot will be unbound.  Note that assigning nil to a slot still makes it bound.

We start with slot-boundp.  This function allows the programmer to determine whether or not a particular named slot in an instance has been bound.  The most likely place to use this is in an :after method specialized on the class for the initialize-instance generic function.  The programmer can use it to determine whether the slot was initialized, perhaps via an :initarg invocation, and take appropriate action to fill in the variable if no such value was assigned.

Here is a short transcript showing the use of slot-boundp:
*slime-repl sbcl*

CL-USER> (defclass test-class ()
           ((slot-1             :accessor get-1 
                                :initform nil)
            (slot-2             :accessor get-2)))
#<STANDARD-CLASS TEST-CLASS>
CL-USER> (slot-boundp (make-instance 'test-class) 'slot-1)
T
CL-USER> (slot-boundp (make-instance 'test-class) 'slot-2)
NIL
CL-USER> (slot-boundp (make-instance 'test-class) 'slot-3)
; Evaluation aborted on #<SIMPLE-ERROR "~@<When attempting to ~A, the slot ~S is missing from the ~
          object ~S.~@:>" {100338F633}>.

Note that if I call slot-boundp on a slot name that is not defined in the class, an error is signaled.  This function does not enable the programmer to determine whether a particular slot name is in the definition of the class, merely whether a certain slot, known to be in the definition, is bound to a value in a particular instance of this class.