Implement ordered dicts in terms of generics.

This commit is contained in:
Vincent St-Amour 2012-05-09 17:24:43 -04:00 committed by Asumu Takikawa
parent 17bb9073b9
commit a68242e4eb
4 changed files with 72 additions and 57 deletions

View File

@ -2,15 +2,21 @@
(require racket/dict (require racket/dict
racket/contract/base racket/contract/base
racket/string racket/string
ffi/unsafe/atomic) ffi/unsafe/atomic
generics)
(define ordering/c (define ordering/c
(or/c '= '< '>)) (or/c '= '< '>))
(provide ordering/c) (provide ordering/c)
(define-values (prop:ordered-dict ordered-dict? ordered-dict-ref) (define-generics (ordered-dict prop:ordered-dict ordered-dict?)
(make-struct-type-property 'ordered-dict #f)) (dict-iterate-least ordered-dict)
(dict-iterate-greatest ordered-dict)
(dict-iterate-least/>? ordered-dict key)
(dict-iterate-least/>=? ordered-dict key)
(dict-iterate-greatest/<? ordered-dict key)
(dict-iterate-greatest/<=? ordered-dict key))
(define extreme-contract (define extreme-contract
(->i ([d ordered-dict?]) (->i ([d ordered-dict?])
@ -22,9 +28,10 @@
[_r (d) (or/c #f (dict-iter-contract d))])) [_r (d) (or/c #f (dict-iter-contract d))]))
(define prop:ordered-dict-contract (define prop:ordered-dict-contract
(let ([e extreme-contract] (let ([e (or/c extreme-contract #f)] ;; generics initializes with #f,
[s search-contract]) ; then sets the methods
(vector-immutable/c e ;; iterate-least [s (or/c search-contract #f)])
(vector/c e ;; iterate-least
e ;; iterate-greatest e ;; iterate-greatest
s ;; iterate-least/>? s ;; iterate-least/>?
s ;; iterate-least/>=? s ;; iterate-least/>=?
@ -33,23 +40,7 @@
;; -------- ;; --------
(define-syntax-rule (appd d offset arg ...) (provide ordered-dict)
(let ([dv d])
((vector-ref (ordered-dict-ref dv) offset) dv arg ...)))
(define (dict-iterate-least d)
(appd d 0))
(define (dict-iterate-greatest d)
(appd d 1))
(define (dict-iterate-least/>? d k)
(appd d 2 k))
(define (dict-iterate-least/>=? d k)
(appd d 3 k))
(define (dict-iterate-greatest/<? d k)
(appd d 4 k))
(define (dict-iterate-greatest/<=? d k)
(appd d 5 k))
(provide/contract (provide/contract
[prop:ordered-dict [prop:ordered-dict
(struct-type-property/c prop:ordered-dict-contract)] (struct-type-property/c prop:ordered-dict-contract)]

View File

@ -3,7 +3,8 @@
(for-label data/order (for-label data/order
racket/contract racket/contract
racket/dict racket/dict
racket/base)) racket/base
generics))
@title{Orders and Ordered Dictionaries} @title{Orders and Ordered Dictionaries}
@ -23,15 +24,19 @@ Contract for orderings, represented by the symbols @racket['=],
@racket['<], and @racket['>]. @racket['<], and @racket['>].
} }
@deftogether[[
@defthing[ordered-dict any/c]
@defthing[prop:ordered-dict @defthing[prop:ordered-dict
(struct-type-property/c (struct-type-property/c
(vector-immutableof _e/c _e/c _s/c _s/c _s/c _s/c))]{ (vectorof _e/c _e/c _s/c _s/c _s/c _s/c))]
]]{
Struct-type property for defining new ordered dictionary types. The Struct-type property for defining new ordered dictionary types.
value associated with @racket[prop:ordered-dict] should be an Methods can be attached to the @racket[prop:ordered-dict] struct property
immutable vector of six procedures, two ``extrema'' procedures and using the @racket[methods] form and the @racket[ordered-dict] generic
four ``search'' procedures. The extrema procedures must satisfy interface. Two ``extrema'' methods and four ``search'' methods should be
@racket[_e/c] and the search procedures must satisfy @racket[_s/c]: implemented. The extrema methods must satisfy @racket[_e/c] and the search
methods must satisfy @racket[_s/c]:
@racketblock[ @racketblock[
_e/c = (->i ([d ordered-dict?]) _e/c = (->i ([d ordered-dict?])
@ -41,7 +46,7 @@ _s/c = (->i ([d ordered-dict?]
[_ (d) (or/c #f (dict-iter-contract d))]) [_ (d) (or/c #f (dict-iter-contract d))])
] ]
The procedures are implementations of the following generic functions: The methods are implementations of the following generic functions:
@itemize[ @itemize[
@item{@racket[dict-iterate-least]} @item{@racket[dict-iterate-least]}

View File

@ -2,6 +2,7 @@
(require racket/match (require racket/match
racket/contract/base racket/contract/base
racket/dict racket/dict
generics
"order.rkt") "order.rkt")
;; owned by ryanc ;; owned by ryanc
@ -350,20 +351,19 @@ Levels are indexed starting at 1, as in the paper.
skip-list-iterate-key skip-list-iterate-key
skip-list-iterate-value)) skip-list-iterate-value))
(define ordered-dict-methods
(vector-immutable skip-list-iterate-least
skip-list-iterate-greatest
skip-list-iterate-least/>?
skip-list-iterate-least/>=?
skip-list-iterate-greatest/<?
skip-list-iterate-greatest/<=?))
(struct skip-list ([head #:mutable] [num-entries #:mutable] =? <?) (struct skip-list ([head #:mutable] [num-entries #:mutable] =? <?)
#:property prop:dict/contract #:property prop:dict/contract
(list dict-methods (list dict-methods
(vector-immutable any/c any/c skip-list-iter? (vector-immutable any/c any/c skip-list-iter?
#f #f #f)) #f #f #f))
#:property prop:ordered-dict ordered-dict-methods) #:property prop:ordered-dict
(methods ordered-dict
(define dict-iterate-least skip-list-iterate-least)
(define dict-iterate-greatest skip-list-iterate-greatest)
(define dict-iterate-least/>? skip-list-iterate-least/>?)
(define dict-iterate-least/>=? skip-list-iterate-least/>=?)
(define dict-iterate-greatest/<? skip-list-iterate-greatest/<?)
(define dict-iterate-greatest/<=? skip-list-iterate-greatest/<=?)))
(struct skip-list* skip-list (key-c value-c) (struct skip-list* skip-list (key-c value-c)
#:property prop:dict/contract #:property prop:dict/contract
@ -372,7 +372,14 @@ Levels are indexed starting at 1, as in the paper.
(lambda (s) (skip-list*-key-c s)) (lambda (s) (skip-list*-key-c s))
(lambda (s) (skip-list*-value-c s)) (lambda (s) (skip-list*-value-c s))
#f)) #f))
#:property prop:ordered-dict ordered-dict-methods) #:property prop:ordered-dict
(methods ordered-dict
(define dict-iterate-least skip-list-iterate-least)
(define dict-iterate-greatest skip-list-iterate-greatest)
(define dict-iterate-least/>? skip-list-iterate-least/>?)
(define dict-iterate-least/>=? skip-list-iterate-least/>=?)
(define dict-iterate-greatest/<? skip-list-iterate-greatest/<?)
(define dict-iterate-greatest/<=? skip-list-iterate-greatest/<=?)))
(struct adjustable-skip-list skip-list () (struct adjustable-skip-list skip-list ()
#:property prop:dict/contract #:property prop:dict/contract
@ -387,7 +394,14 @@ Levels are indexed starting at 1, as in the paper.
(lambda (s) (adjustable-skip-list*-key-c s)) (lambda (s) (adjustable-skip-list*-key-c s))
(lambda (s) (adjustable-skip-list*-value-c s)) (lambda (s) (adjustable-skip-list*-value-c s))
#f)) #f))
#:property prop:ordered-dict ordered-dict-methods) #:property prop:ordered-dict
(methods ordered-dict
(define dict-iterate-least skip-list-iterate-least)
(define dict-iterate-greatest skip-list-iterate-greatest)
(define dict-iterate-least/>? skip-list-iterate-least/>?)
(define dict-iterate-least/>=? skip-list-iterate-least/>=?)
(define dict-iterate-greatest/<? skip-list-iterate-greatest/<?)
(define dict-iterate-greatest/<=? skip-list-iterate-greatest/<=?)))
(define (make-skip-list [ord datum-order] (define (make-skip-list [ord datum-order]
#:key-contract [key-contract any/c] #:key-contract [key-contract any/c]

View File

@ -4,6 +4,7 @@
racket/match racket/match
racket/dict racket/dict
racket/contract/base racket/contract/base
generics
"order.rkt") "order.rkt")
#| #|
@ -514,14 +515,6 @@ Options
n:splay-tree-iterate-key n:splay-tree-iterate-key
n:splay-tree-iterate-value)) n:splay-tree-iterate-value))
(define n:ordered-dict-methods
(vector-immutable n:splay-tree-iterate-least
n:splay-tree-iterate-greatest
n:splay-tree-iterate-least/>?
n:splay-tree-iterate-least/>=?
n:splay-tree-iterate-greatest/<?
n:splay-tree-iterate-greatest/<=?))
(struct node-splay-tree ([root #:mutable] [size #:mutable]) (struct node-splay-tree ([root #:mutable] [size #:mutable])
#:property prop:dict/contract #:property prop:dict/contract
(list n:dict-methods (list n:dict-methods
@ -530,7 +523,13 @@ Options
splay-tree-iter? splay-tree-iter?
#f #f #f)) #f #f #f))
#:property prop:ordered-dict #:property prop:ordered-dict
n:ordered-dict-methods) (methods ordered-dict
(define dict-iterate-least n:splay-tree-iterate-least)
(define dict-iterate-greatest n:splay-tree-iterate-greatest)
(define dict-iterate-least/>? n:splay-tree-iterate-least/>?)
(define dict-iterate-least/>=? n:splay-tree-iterate-least/>=?)
(define dict-iterate-greatest/<? n:splay-tree-iterate-greatest/<?)
(define dict-iterate-greatest/<=? n:splay-tree-iterate-greatest/<=?)))
(struct node-splay-tree* node-splay-tree (key-c value-c) (struct node-splay-tree* node-splay-tree (key-c value-c)
#:property prop:dict/contract #:property prop:dict/contract
@ -542,7 +541,13 @@ Options
(lambda (s) (node-splay-tree*-value-c s)) (lambda (s) (node-splay-tree*-value-c s))
#f)) #f))
#:property prop:ordered-dict #:property prop:ordered-dict
n:ordered-dict-methods) (methods ordered-dict
(define dict-iterate-least n:splay-tree-iterate-least)
(define dict-iterate-greatest n:splay-tree-iterate-greatest)
(define dict-iterate-least/>? n:splay-tree-iterate-least/>?)
(define dict-iterate-least/>=? n:splay-tree-iterate-least/>=?)
(define dict-iterate-greatest/<? n:splay-tree-iterate-greatest/<?)
(define dict-iterate-greatest/<=? n:splay-tree-iterate-greatest/<=?)))