From: goose
Subject: Writing classes to files and reading them back in
Date: 
Message-ID: <1127719500.787195.255650@g47g2000cwa.googlegroups.com>
Hello once again everyone.

I'd like to write my objects to a file and read them
back in later. They need not be portable between different
implementations.

example:

(defvar *id-set* 0)

(defclass unique ()
  ((id
    :initarg :id
    :initform (setf *id-set* (+ 1 *id-set*)))))


(defclass transaction (unique)
  ((amount
    :initarg :amount
    :initform 0)
   (details
    :initarg :details
    :initform nil)))


(defun write-class ...)


What I want to do is have a generic function (or macro)
which can take any class and write it to a file in a manner
that would enable me to read it back in after the program
restarts.


TIA, HAND
L. K. Manickum

From: ·············@specastro.com
Subject: Re: Writing classes to files and reading them back in
Date: 
Message-ID: <1127750214.397669.82020@g47g2000cwa.googlegroups.com>
goose wrote:
> Hello once again everyone.
>
> I'd like to write my objects to a file and read them
> back in later. They need not be portable between different
> implementations.
>

Have you looked at http://common-lisp.net/project/cl-store/?  I've been
using it lately and it works quite well.

Glenn Ehrlich
http://cooking-with-lisp.blogspot.com/
From: Marco Baringer
Subject: Re: Writing classes to files and reading them back in
Date: 
Message-ID: <m2k6h4wa7e.fsf@soma.local>
"goose" <····@webmail.co.za> writes:

> What I want to do is have a generic function (or macro)
> which can take any class and write it to a file in a manner
> that would enable me to read it back in after the program
> restarts.

how much data are we talking about? if you're just looking for
something quick and simple try this:

(defvar *objects* nil
  "Put all the objects you want to save here.")

(defun write-objects ()
  (with-open-file ("file.lisp" file :direction :output)
    (write-line "(cl:in-package :my-package)" file)
    (write-line "(setf *objects* '#.*objects*)" file))
  (compile-file "file.lisp"))

(defun load-objects ()
  (load (compile-file-pathname "file.lisp")))

if you've got more data than can fit in ram (or you violate some
implementation depedent limit on compiled files) then you'll need to
use something more complex (clsql, cl-store, elephant, etc.)

hth.

-- 
-Marco
Ring the bells that still can ring.
Forget the perfect offering.
There is a crack in everything.
That's how the light gets in.
	-Leonard Cohen
From: Russell McManus
Subject: Re: Writing classes to files and reading them back in
Date: 
Message-ID: <87k6h4oy6h.fsf@cl-user.org>
"Marco Baringer" <··@bese.it> writes:

> "goose" <····@webmail.co.za> writes:
>
>> What I want to do is have a generic function (or macro)
>> which can take any class and write it to a file in a manner
>> that would enable me to read it back in after the program
>> restarts.
>
> how much data are we talking about? if you're just looking for
> something quick and simple try this:
>
> (defvar *objects* nil
>   "Put all the objects you want to save here.")
>
> (defun write-objects ()
>   (with-open-file ("file.lisp" file :direction :output)
>     (write-line "(cl:in-package :my-package)" file)
>     (write-line "(setf *objects* '#.*objects*)" file))
>   (compile-file "file.lisp"))
>
> (defun load-objects ()
>   (load (compile-file-pathname "file.lisp")))
>
> if you've got more data than can fit in ram (or you violate some
> implementation depedent limit on compiled files) then you'll need to
> use something more complex (clsql, cl-store, elephant, etc.)

You can use the file compiler to compile a source code expression
containing your objects.  Then you can just use the LOAD function to
load the compiled code back in.  This is likely to be plenty faster
than solutions based on READ.

Perhaps an example would be helpful:

(defun load-web-data (&key (dir *web-dir*)
                           (name "web-data"))
  (load (compile-file-pathname
         (make-pathname :defaults dir
                        :name name)))
  (setf *web-id*
        (max *web-id*
             (1+ (loop for instance in *web-instances*
                       maximize (web-id instance))))))

(defun dump-web-data (&key (dir *web-dir*)
                           (name "web-data"))
  (let ((cf (make-pathname :defaults dir
                           :name name
                           :type "lisp")))
    (with-open-file (s cf
                       :direction :output
                       :if-exists :supersede
                       :if-does-not-exist :create)
      (dolist (var '(*web-instances*))
        (format s "(setf ~S '#.~S)" var var)))
    (compile-file cf :output-file
                  (compile-file-pathname
                   (make-pathname :defaults cf :type nil)))))

The objects in *web-instances* must participate in the MAKE-LOAD-FORM
protocol for this to work.

-russ