;; First of some benchmarking to show of some code
(define n 10000000)
(define (test)
(with-stis-hash ((h ref))
(let lp ((i 0) (s 0))
(if (< i n)
(lp (+ i 1) (+ s (ref h (modulo i 1000))))
s))))
(define (test2)
(let lp ((i 0) (s 0))
(if (< i n)
(lp (+ i 1) (+ s (hashq-ref H (modulo i 1000))))
s)))
scheme@(guile-user)> ,time (test)
$11 = 4995000000
;; 0.268354s real time, 0.268264s run time. 0.000000s spent in GC.
scheme@(guile-user)> ,time (test2)
$12 = 4995000000
;; 0.448963s real time, 0.448837s run time. 0.000000s spent in GC.
Nice eh!
------------------------------------------------
API
------------------------------------------------
;; Load the module,
(use-modules (ice-9 stis-hash))
;; Anyhow to create a stis hash table you need to use,
(define m (make-stis-hash-table 'hashq 10000 #:name 'test))
;; pre defined types are 'hashq 'hashv and 'hash
;; we can make a new type by
(define myhash (lambda (x) (logxor (hashq x 10) (hashv x 10))))
(make-stis-hash-type 'my myhash equal?)
;; and use it by
(define m (make-stis-hash-table 'my 10000 #:name 'test))
;; We have
stis-hash-ref
stis-hash-set!
stis-hash-remove!
;; which is similar to the guile interface. But in order to
;; be fast us with-stis-hash like
(with-stis-hash ((h ref )) code ...)
(with-stis-hash ((h ref set )) code ...)
(with-stis-hash ((h ref set rem)) code ...)
;; we can use _ to indicate that this part is not used,
;; the the interface is the same as other hash accessors
;; but the hash-table is implicit and remeved as argument
;; Finally we can loop using functional constructions like
stis-hash-for-each
stis-hash-fold
stis-hash-map
;; which are much much faster than guile vanilla hashes and
;; uses only pure scheme
This uses a modified guile with v, instructions for hash-ref parts and hash calc functions. In that guile branch I also have the one shot continuation code as well.
Refereces: