Проблема такова (SBCL)
(defclass c1 () ((i :initform 1)))
(defparameter *i1* (make-instance 'c1))
(defclass c1 () ((i :initform 1)(j :initform (print "Ura"))))
(trace update-instance-for-redefined-class)
(defclass c1 () ((i :initform 1)))
(slot-value *i1* 'i)
0: (UPDATE-INSTANCE-FOR-REDEFINED-CLASS #<C1 {253D0051}> NIL NIL NIL)
0: UPDATE-INSTANCE-FOR-REDEFINED-CLASS returned #<C1 {253D0051}>
«Ura» не напечаталось вовсе. Умный рантайм оптимизировал процесс эволюции и класс сразу скакнул в своей эволюции из первобытно-общинного строя в социализм, минуя промежуточную версию. Если бы мы между изменениями класса обратились к сущности, то прогресс прошёл бы за два этапа.
Поэтому приведённый вот здесь
http://www.lispworks.com/documentation/HyperSpec/Body/f_upda_1.htm#update-ins...
пример про превращение прямоугольных координат в полярные - на самом деле будет работать только с оговорками.
Если мы потом захотим преобразовать полярные координаты ещё в какие-то, а потом ещё и ещё, то нам нужно будет написать не N ветвей на каждый этап эволюции, а N*(N-1), на скачок от любой версии к любой другой. Плюс может оказаться нетривиальной задачей понять, откуда и куда мы мигрируем. Впрочем, это не так уж и тяжело - (наверное) достаточно завести слот «номер версии», который будем заменять другим на каждом шаге. Типа такого:
(unintern 'c1)
(unintern '*i1*)
(defclass c1 () ((i :initform 1) (version1 :initform nil)))
(defparameter *i1* (make-instance 'c1))
(defclass c1 ()
((i :initform 1)
(j :initform (print "Ura"))
(version2 :initform nil)))
(trace update-instance-for-redefined-class)
(defclass c1 ()
((i :initform 1)
(version3 :initform nil)
))
(slot-value *i1* 'i)
0: (UPDATE-INSTANCE-FOR-REDEFINED-CLASS #<C1 {24134041}> (VERSION3) (VERSION1) (VERSION1 NIL))
0: UPDATE-INSTANCE-FOR-REDEFINED-CLASS returned #<C1 {24134041}>
Дальнейшую глубину ситуации придаёт то, что никогда нет гарантии, что у нас в системе не осталось старых экземпляров от самой первой версии, даже если текущая версия - 100500. Поэтому мы должны будем хранить все ветви алгоритма обновления вечно.
А теперь - почему у меня с этим проблемы. Я захотел довольно простую (казалось бы) вещь - поменять тип поля с числа на строку с сохранением данных. Данные должны преобразоваться в строку с помощью prin1-to-string.
Тут вопроса, собственно, нет. Это просто пока что мысли вслух :)