[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
initialization meeting notes
- To: Common-Lisp-Object-System@Sail.Stanford.edu
- Subject: initialization meeting notes
- From: Gregor.pa@Xerox.COM
- Date: Thu, 23 Jul 87 18:09 PDT
- Line-fold: no
In this message I try to summarize what we agreed at the meeting in
Boston. The basis for this message is the 4 pages of notes which Sonya
took and which Sonya, Dave and I went over just before the meeting
ended. I have tried to include in this message only what we actually
agreed on. I will send out my comments and suggestions in a separate
message.
First, a brief summary of what we agreed:
- there will be a :initarg slot option
- will will support remote initarg defaulting by having an
defclass option like :default-initargs.
- there will be a procedural model of how the whole thing
works. Extensions to initialization behavior other than
simple-slot-filling-initargs and initarg-remote-defaulting
will be done by defining a method on the appropriate generic
function.
Another important thing which we agreed is that we are going to have to
go back and re-examine our rules for argument list congruence. The
existing rules clearly get in our way for doing initialization. In a
separate message I will try to summarize those problems.
In the meeting, we put up some code for make-instance and
initialize-instance. I am including that here:
(defmethod make-instance ((class-name 'symbol) &rest initargs)
(apply #'make-instance (class-named class-name) initargs))
(defmethod make-instance ((class standard-class) &rest initargs)
(let* ((proto (class-prototype class))
(defaulted-initargs (default-initargs proto initargs)))
(check-initargs class defaulted-initargs)
(let ((instance (apply #'allocate-instance class defaulted-initargs)))
(apply #'initialize-instance instance defaulted-initargs)
instance)))
(defmethod initialize-instance ((obj object) &rest initargs)
;; The default initialize-instance method deals with setting the
;; values of slots from slot-filling-initargs and from initforms.
;;
;; The rules are that the leftmost initarg which is declared
;; as setting a slot (with the :initarg slot option) actually
;; does set it (or is it the rightmost?); and that slots which
;; are not set by an initarg have their :initform evaluated and
;; used to set them.
)
An effect of putting the slot setting stuff in the default method on
initialize-instance is that most programmers will want to define their
initialize-instance methods as :after methods. This means an instance
will get initialized in order from most general to least general.
The default method for default-initargs implements the initarg remote
defaulting behavior using the :default-initargs class option.
The default method for check-initargs checks the validity of the
initargs by checking two sources:
1. an initarg is valid if it is specified as a slot-filling initarg.
2. an initarg is valid if it is specified as a &key argument in
one of the applicable methods on initialize-instance.
Here is an example of a use of this protocol:
(defclass ship ()
((x :initarg :x)
(y :initarg :y)))
(defmethod initialize-instance :after ((s ship) &key startp)
(when startp (start s)))
(defmethod start ((s ship))
(with-slots ((s :use-accesors nil))
(if (and x y)
<start it up>
(error "Have to set X and Y before starting a ship."))))
(defclass homing-ship (ship)
()
(:default-initargs
:x 0
:y 0))
(defmethod home ((s homing-ship))
(with-slots ((s :use-accessors nil))
(setq x 0 y 0)))
We also agreed that there would be documented functions for finding out
about the initargs that set slots for a class and also finding out about
the default initargs for a class. This doesn't seem to be too hard;
the only serious problem has to do with arranging for a the default
initarg value forms to be evaluated in the lexical environment of the
defclass. (Of course if environments were first class objects this would
be trivial...)
-------