Standard Generic Function UPDATE-INSTANCE-FOR-REDEFINED-CLASS

Syntax

  • update-instance-for-redefined-class instance added-slots discarded-slots property-list &rest initargs &key &allow-other-keysresult*

Method Signatures

  • update-instance-for-redefined-class (instance standard-object) added-slots discarded-slots property-list &rest initargs

Arguments and Values

Description

The generic function update-instance-for-redefined-class is not intended to be called by programmers. Programmers may write methods for it. The generic function update-instance-for-redefined-class is called by the mechanism activated by make-instances-obsolete.

The system-supplied primary method on update-instance-for-redefined-class checks the validity of initargs and signals an error if an initarg is supplied that is not declared as valid. This method then initializes slots with values according to the initargs, and initializes the newly added-slots with values according to their :initform forms. It does this by calling the generic function shared-initialize with the following arguments: the instance, a list of names of the newly added-slots to instance, and the initargs it received. Newly added-slots are those local slots for which no slot of the same name exists in the old version of the class.

When make-instances-obsolete is invoked or when a class has been redefined and an instance is being updated, a property-list is created that captures the slot names and values of all the discarded-slots with values in the original instance. The structure of the instance is transformed so that it conforms to the current class definition. The arguments to update-instance-for-redefined-class are this transformed instance, a list of added-slots to the instance, a list discarded-slots from the instance, and the property-list containing the slot names and values for slots that were discarded and had values. Included in this list of discarded slots are slots that were local in the old class and are shared in the new class.

The value returned by update-instance-for-redefined-class is ignored.

Examples

(defclass coords () ())

#<STANDARD-CLASS COMMON-LISP-USER::COORDS>

(defclass x-y-coords (coords) ((x :initform 0 :accessor coords-x) (y :initform 0 :accessor coords-y)))

#<STANDARD-CLASS COMMON-LISP-USER::X-Y-COORDS>

It turns out polar coordinates are used more than Cartesian coordinates, so the representation is altered and some new accessor methods are added.

The :before method on update-instance-for-redefined-class defined below transforms the x-y coordinates to polar coordinates and stores them into the new slots.

(defmethod update-instance-for-redefined-class :before (pos x-y-coords) added deleted plist &key) (let ((x (getf plist 'x)) (y (getf plist 'y))) (setf (coords-rho pos) (sqrt (+ (* x x) (* y y))) (coords-theta pos) (atan y x))))

#<STANDARD-METHOD COMMON-LISP:UPDATE-INSTANCE-FOR-REDEFINED-CLASS :BEFORE (X-Y-COORDS T T T) {100273D1C3}>

(defclass x-y-coords (coords) ((rho :initform 0 :accessor coords-rho) (theta :initform 0 :accessor coords-theta)))

#<STANDARD-CLASS COMMON-LISP-USER::X-Y-COORDS>

All instances of the old x-y-coords class will be updated automatically.

The new representation is given the look and feel of the old one.

(defmethod coords-x ((pos x-y-coords)) (with-slots (rho theta) pos (* rho (cos theta))))

#<STANDARD-METHOD COMMON-LISP-USER::POSITION-X (X-Y-POSITION) {10027FC4E3}>

(defmethod (setf coords-x) (new-x (pos x-y-coords)) (with-slots (rho theta) pos (let ((y (coords-y pos))) (setf rho (sqrt (+ (* new-x new-x) (* y y))) theta (atan y new-x)) new-x)))

#<STANDARD-METHOD (COMMON-LISP:SETF COMMON-LISP-USER::POSITION-X) (T X-Y-POSITION) {1002842601}>

(defmethod coords-y ((pos x-y-coords)) (with-slots (rho theta) pos (* rho (sin theta))))

#<STANDARD-METHOD COMMON-LISP-USER::POSITION-Y (X-Y-POSITION) {10027FC1F9}>

(defmethod (setf coords-y) (new-y (pos x-y-coords)) (with-slots (rho theta) pos (let ((x (coords-x pos))) (setf rho (sqrt (+ (* x x) (* new-y new-y))) theta (atan new-y x))

#<STANDARD-METHOD (COMMON-LISP:SETF COMMON-LISP-USER::POSITION-Y) (T X-Y-POSITION) {10028766D3}>

Affected By

None.

Exceptional Situations

The system-supplied primary method on update-instance-for-redefined-class signals an error if an initarg is supplied that is not declared as valid.

See Also

Notes

initargs are declared as valid by using the :initarg option to defclass, or by defining methods for update-instance-for-redefined-class or shared-initialize. The keyword name of each keyword parameter specifier in the lambda list of any method defined on update-instance-for-redefined-class or shared-initialize is declared as a valid initarg name for all classes for which that method is applicable.

\issue{INITIALIZATION-FUNCTION-KEYWORD-CHECKING}