unofficial mirror of guile-devel@gnu.org 
 help / color / mirror / Atom feed
* Optimizing record accessors
@ 2007-08-07 15:00 Ludovic Courtès
  2007-08-08 15:08 ` Ludovic Courtès
  2007-08-21  0:10 ` Kevin Ryde
  0 siblings, 2 replies; 4+ messages in thread
From: Ludovic Courtès @ 2007-08-07 15:00 UTC (permalink / raw)
  To: guile-devel

[-- Attachment #1: Type: text/plain, Size: 1903 bytes --]

Hi,

Currently, accessing a record is slow.  Consider this sample:

===File ~/src/guile-core/,,record-prof.scm==================
(use-modules (statprof)
             (srfi srfi-9))

(define-record-type <stuff>
  (make-stuff x y z)
  stuff?
  (x  stuff-x)
  (y  stuff-y)
  (z  stuff-z))

(define stuff (make-stuff 1 2 3))

(with-statprof #:hz 20 #:loop 1000000
  (stuff-x stuff))
============================================================

(SRFI-9 uses the record layer.)

Here is what we observe:

  $ ./pre-inst-guile ,,record-prof.scm
  %     cumulative   self             
  time   seconds     seconds      name
   33.33      2.95      0.98  #{statprof\ 0}#
   27.45      0.81      0.81  record-type-descriptor
   17.65      1.91      0.52  stuff-x
   15.69      1.39      0.46  %record-type-check
    3.92      0.93      0.12  eq?
    1.96      0.06      0.06  not
  ---
  Sample count: 51
  Total time: 2.95 seconds (9/25 seconds in GC)

Changing `record-accessor' as in the attached file yields this:

  $ ./pre-inst-guile ,,record-prof.scm
  %     cumulative   self             
  time   seconds     seconds      name
   46.88      1.89      0.89  #{statprof\ 0}#
   43.75      0.95      0.83  stuff-x
    6.25      0.12      0.12  eq?
    3.13      0.06      0.06  not
  ---
  Sample count: 32
  Total time: 1.89 seconds (1/5 seconds in GC)

A 36% improvement.

Type-safety is still guaranteed (e.g., `struct-vtable' will fail if OBJ
is not a struct), though not as precisely (e.g., instead of a
`not-a-record' error, we get a `wrong-type-arg' error in
`struct-vtable').  Thus, for instance, `srfi-9.test' will have to be
relaxed as to the exception type expected (which is reasonable anyway
since SRFI-9 does not specify error types).

I believe the improvement is worth the change, otherwise people may end
up using vectors or their own record abstraction.

Ok to commit?

Thanks,
Ludovic.


[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: Optimized record accessors --]
[-- Type: text/x-patch, Size: 1205 bytes --]

--- orig/ice-9/boot-9.scm
+++ mod/ice-9/boot-9.scm
@@ -429,7 +429,7 @@
 (define (record-predicate rtd)
   (lambda (obj) (and (struct? obj) (eq? rtd (struct-vtable obj)))))
 
-(define (%record-type-check rtd obj)  ;; private helper
+(define (%record-type-error rtd obj)  ;; private helper
   (or (eq? rtd (record-type-descriptor obj))
       (scm-error 'wrong-type-arg "%record-type-check"
 		 "Wrong type record (want `~S'): ~S"
@@ -441,8 +441,9 @@
     (if (not pos)
 	(error 'no-such-field field-name))
     (local-eval `(lambda (obj)
-		   (%record-type-check ',rtd obj)
-		   (struct-ref obj ,pos))
+                   (if (eq? (struct-vtable obj) ,rtd)
+                       (struct-ref obj ,pos)
+                       (%record-type-error ,rtd obj)))
 		the-root-environment)))
 
 (define (record-modifier rtd field-name)
@@ -450,7 +451,8 @@
     (if (not pos)
 	(error 'no-such-field field-name))
     (local-eval `(lambda (obj val)
-		   (%record-type-check ',rtd obj)
-		   (struct-set! obj ,pos val))
+                   (if (eq? (struct-vtable obj) ,rtd)
+                       (struct-set! obj ,pos val)
+                       (%record-type-error ,rtd obj)))
 		the-root-environment)))
 

[-- Attachment #3: Type: text/plain, Size: 143 bytes --]

_______________________________________________
Guile-devel mailing list
Guile-devel@gnu.org
http://lists.gnu.org/mailman/listinfo/guile-devel

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2007-08-21  7:58 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2007-08-07 15:00 Optimizing record accessors Ludovic Courtès
2007-08-08 15:08 ` Ludovic Courtès
2007-08-21  0:10 ` Kevin Ryde
2007-08-21  7:58   ` Ludovic Courtès

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).