PasteRack.org
Paste # 78355
2014-08-20 20:05:44

Forked from paste # 22095.

Fork as a new paste.

Paste viewed 128 times.


Embed:

  1. #lang racket
  2. (require racket/pretty)
  3. (provide insert lookup btree)
  4.  
  5. (struct Btree (tree = > <) #:transparent)
  6. (struct Empty ())
  7. (struct Node (key value size left right) #:transparent)
  8.  
  9. (define (btree = > <)
  10.   (Btree (Empty) = > <))
  11.  
  12. (define (node-size n)
  13.   (match n
  14.     [(Empty) 0]
  15.     [(Node _ _ s _ _) s]))
  16.  
  17. (define (insert-aux tree k v = > <)
  18.   (match tree
  19.     [(Node tk tvs ts tl tr)
  20.      (cond
  21.        [(= tk k) (Node tk (set-add tvs v) ts tl tr)]
  22.        [(> tk k) (let* ([new-left (insert-aux tl k v = > <)]
  23.                         [new-size (+ 1 (node-size new-left) (node-size tr))])
  24.                    (Node tk tvs new-size new-left tr))]
  25.        [(< tk k) (let* ([new-right (insert-aux tr k v = > <)]
  26.                         [new-size (+ 1 (node-size tl) (node-size new-right))])
  27.                    (Node tk tvs new-size tl new-right))])]
  28.     [(Empty) (Node k (set v) 1 (Empty) (Empty))]))
  29.  
  30. (define (insert btree k v)
  31.   (match-let ([(Btree tree = > <) btree])
  32.     (Btree (insert-aux tree k v = > <) = > <)))
  33.  
  34. (define (insert*  btree . inits)
  35.   (foldl (lambda (x m) (insert m (first x) (second x))) btree inits))
  36.  
  37.  
  38. (define (lookup-aux tree k = > <)
  39.   (match tree
  40.     [(Node tk tvs ts tl tr)
  41.      (cond
  42.        [(= tk k) tvs]
  43.        [(> tk k) (lookup-aux tl k = > <)]
  44.        [(< tk k) (lookup-aux tr k = > <)])]
  45.     [(Empty) (set)]))
  46.  
  47. (define (lookup btree k)
  48.   (match-let ([(Btree tree = > <) btree])
  49.     (lookup-aux tree k = > <)))
  50.  
  51. (define (yield-tree yield tree)
  52.   (match tree
  53.     [(Node tk tvs ts tl tr)
  54.      (yield-tree yield tl)
  55.      (yield (list tk tvs))
  56.      (yield-tree yield tr)]
  57.     [(Empty) (void)]))
  58.  
  59. (define (btree->vector bt)
  60.   (let ([i 0]
  61.         [buffer (make-vector (node-size (Btree-tree bt)))])
  62.     (yield-tree
  63.      (lambda (x)
  64.        (vector-set! buffer i x)
  65.        (set! i (add1 i))
  66.        i)
  67.      (Btree-tree bt))
  68.     buffer))
  69.  
  70. (define (btree->alist bt)
  71.   (vector->list (btree->vector bt)))
  72.  
  73. (define (alist->btree alist bt)
  74.   (match-let ([(Btree tree = > <) bt])
  75.       (foldl (lambda (pair tree)
  76.                (insert tree (car pair) (cadr pair)))
  77.              bt
  78.              alist)))
  79.  
  80. (define (partial-lookup-aux tree k = > <)
  81.   (match tree
  82.     [(Node tk tvs ts tl tr)
  83.      `(cond
  84.          [(,= ,tk ,k) ,(cons 'list (set->list tvs))]
  85.          [(,> ,tk ,k) ,(partial-lookup-aux tl k = > <)]
  86.          [(,< ,tk ,k) ,(partial-lookup-aux tr k = > <)])]
  87.     [(Empty) '(list)]))
  88.  
  89. (define (partial-lookup btree k)
  90.   (match-let ([(Btree tree = > <) btree])
  91.     ;; procedures need quoted reprs
  92.     (let ([= '=] [> '>] [< '<])
  93.       (partial-lookup-aux tree k = > <))))
  94.  
  95.  
  96. (define test-cases '((1 'a) (2 'b) (3 'c) (1 'd)))
  97. (define tree1 (alist->btree test-cases (btree = > <)))
  98. (define pevald #`(lambda (x) #,(partial-lookup tree1 #'x)))
  99. (define runnable (eval pevald))
  100. (pretty-print (syntax->datum pevald))
  101. #| =>
  102. '(lambda (x)
  103.    (cond
  104.     ((= 1 x) (list 'a 'd))
  105.     ((> 1 x) (list))
  106.     ((< 1 x)
  107.      (cond
  108.       ((= 2 x) (list 'b))
  109.       ((> 2 x) (list))
  110.       ((< 2 x)
  111.        (cond ((= 3 x) (list 'c)) ((> 3 x) (list)) ((< 3 x) (list))))))))
  112. |#
  113.  
  114. (map runnable '(1 2 3))
  115. ;; => '((a d) (b) (c))

=>