Tag Archives: programming

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

The slot-unbound standard generic function is invoked when an attempt to read an unbound, but existing slot in an instance is made (if this explanation is unclear, please review the earlier article on slot-boundp).  Once more, this function is not for the programmer to call into, but by specializing this function it is possible to take special action when an attempt is made to read the contents of an unbound slot.

In effect, slot-unbound has the same relationship to slot-boundp that slot-missing has to slot-exists-p.

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

The slot-missing generic function is a function that is not intended to be invoked by the programmer, but it’s still interesting to the programmer in some contexts.  This generic function is invoked by the Lisp system when an attempt is made to retrieve from an instance the value of a slot that doesn’t exist in the class.

By specializing this function, the programmer can attach particular actions to such invalid access attemps.  The ways to access a slot by name in an object are slot-value (with or without its setf operator), slot-boundp, and slot-makunbound.  The invocation of slot-missing allows the programmer to distinguish between these cases.  One possible use would be to add debugging information or logging when one of these invalid accesses is attempted.

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

Earlier, we discussed slot-boundp.  A named slot in an instance will not be bound to a value until it has been assigned by one of several means.  An unbound slot does not have a nil value, it has no value at all, and it is an error to attempt to read its contents.

Under some circumstances, the programmer may want to take a slot that has an associated value, and return it to that pristine, unbound state.  This is what slot-makunbound does.  If the slot has a bound value, that value is discarded and the slot is returned to the unbound state.

The less-familiar parts of Lisp for beginners — slot-exists-p

In our last article, we talked about slots in classes.  I mentioned there that slot-boundp could not tell you whether a particular named slot was present in a class, it raises an error if you ask that function to act on a non-existent slot name.

So, how do you find out whether a particular object has a slot of a given name?  That’s where slot-exists-p comes in.  It returns non-nil if the named slot exists in the instance, either directly or through inheritance.

Why would a programmer want to do this?  When does the programmer not know the names of the slots in a particular class, and should he or she really be messing with a class about which they know so very little?  Well, if the coding specification for a project is sufficiently detailed, one might, for instance, say that programmer-defined classes are permitted, but not required, to define a slot called “time-last-modified”, and if that slot is defined, the code takes action to keep that slot updated.  I’ve seen it used in similar contexts, but rarely.

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.