timothy235

sicp-2-3-3-representing-sets

Feb 24th, 2016
93
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Racket 11.12 KB | None | 0 0
  1. #lang racket
  2.  
  3. ;;;;;;;;;;
  4. ;; 2.59 ;;
  5. ;;;;;;;;;;
  6.  
  7. ;; sets as unordered lists without duplicates
  8.  
  9. (define (element-of-set? x st)
  10.   (cond [(empty? st) #f]
  11.         [(equal? x (first st)) #t]
  12.         [else (element-of-set? x (rest st))]))
  13.  
  14. (define (adjoin-set x st)
  15.   (if (element-of-set? x st) st (cons x st)))
  16.  
  17. (define (intersection-set st1 st2)
  18.   (cond [(or (empty? st1) (empty? st2)) empty]
  19.         [(element-of-set? (first st1) st2)
  20.          (cons (first st1)
  21.                (intersection-set (rest st1) st2))]
  22.         [else (intersection-set (rest st1) st2)]))
  23.  
  24. (define (union-set st1 st2)
  25.   (cond [(empty? st1) st2]
  26.         [(empty? st2) st1]
  27.         [(element-of-set? (first st1) st2)
  28.          (union-set (rest st1) st2)]
  29.         [else (cons (first st1)
  30.                     (union-set (rest st1) st2))]))
  31.  
  32. (define st1 '(0 4 2 1 3))
  33. (define st2 '(5 3 7 4 6))
  34. (element-of-set? 7 st1)
  35. ;; #f
  36. (element-of-set? 4 st1)
  37. ;; #t
  38. (intersection-set st1 st2)
  39. ;; '(4 3)
  40. (union-set st1 st2)
  41. ;; '(0 2 1 5 3 7 4 6)
  42.  
  43. ;;;;;;;;;;
  44. ;; 2.60 ;;
  45. ;;;;;;;;;;
  46.  
  47. ;; sets as unordered lists with duplicates allowed
  48.  
  49. (define (new-adjoin-set x st) (cons x st))
  50.  
  51. (define (new-union-set st1 st2) (append st1 st2))
  52.  
  53. ;; Only adjoin-set and union-set would change.  adjoin-set becomes constant time,
  54. ;; and union-set becomes O(n).  element-of-set? is still O(n) and
  55. ;; intersection-set is still O(n ^ 2).  However, this n is no longer the number of
  56. ;; elements in the set.  n is now the number of elements in the list, which could
  57. ;; be arbitrarily larger.  So allowing duplicates is only something you would do
  58. ;; if you needed to do many adjoin-sets and did not need the other operations to
  59. ;; run efficiently.
  60.  
  61. ;;;;;;;;;;
  62. ;; 2.61 ;;
  63. ;;;;;;;;;;
  64.  
  65. ;; sets as ordered lists
  66.  
  67. (define (ordered-element-of-set? x st)
  68.   (cond [(empty? st) #f]
  69.         [(= x (first st)) #t]
  70.         [(< x (first st)) #f]
  71.         [else (ordered-element-of-set? x (rest st))]))
  72.  
  73. (define (ordered-intersection-set st1 st2)
  74.   (cond [(or (empty? st1) (empty? st2)) empty]
  75.         [else
  76.           (define x1 (first st1))
  77.           (define x2 (first st2))
  78.           (cond [(= x1 x2)
  79.                  (cons x1 (ordered-intersection-set (rest st1) (rest st2)))]
  80.                 [(< x1 x2) (ordered-intersection-set (rest st1) st2)]
  81.                 [else (ordered-intersection-set st1 (rest st2))])]))
  82.  
  83. (define (ordered-adjoin-set x st)
  84.   (cond [(empty? st) (list x)]
  85.         [(= x (first st)) st]
  86.         [(< x (first st)) (cons x st)]
  87.         [else (cons (first st) (ordered-adjoin-set x (rest st)))]))
  88.  
  89. ;; ordered-adjoin-set will terminate when we encounter an element of st that is
  90. ;; bigger than or equal to x.  On average this will happen after examining half
  91. ;; the elements in st.
  92.  
  93. ;;;;;;;;;;
  94. ;; 2.62 ;;
  95. ;;;;;;;;;;
  96.  
  97. (define (ordered-union-set st1 st2)
  98.   (cond [(empty? st1) st2]
  99.         [(empty? st2) st1]
  100.         [else
  101.           (define x1 (first st1))
  102.           (define x2 (first st2))
  103.           (cond [(= x1 x2)
  104.                  (cons x1 (ordered-union-set (rest st1) (rest st2)))]
  105.                 [(< x1 x2)
  106.                  (cons x1 (ordered-union-set (rest st1) st2))]
  107.                 [else (cons x2 (ordered-union-set st1 (rest st2)))])]))
  108.  
  109. (define st3 '(0 1 2 3 4))
  110. (define st4 '(3 4 5 6 7))
  111. (ordered-element-of-set? 7 st3)
  112. ;; #f
  113. (ordered-element-of-set? 4 st3)
  114. ;; #t
  115. (ordered-intersection-set st3 st4)
  116. ;; '(3 4)
  117. (ordered-union-set st3 st4)
  118. ;; '(0 1 2 3 4 5 6 7)
  119.  
  120. ;;;;;;;;;;
  121. ;; 2.63 ;;
  122. ;;;;;;;;;;
  123.  
  124. ;; sets as binary trees
  125.  
  126. (define (entry tree) (first tree))
  127. (define (left-branch tree) (second tree))
  128. (define (right-branch tree) (third tree))
  129. (define (make-tree entry left right) (list entry left right))
  130.  
  131. (define (tree-element-of-set? x st)
  132.   (cond [(empty? st) #f]
  133.         [(= x (entry st)) #t]
  134.         [(< x (entry st))
  135.          (tree-element-of-set? x (left-branch st))]
  136.         [else (tree-element-of-set? x (right-branch st))]))
  137.  
  138. (define (tree-adjoin-set x st)
  139.   (cond [(empty? st) (make-tree x empty empty)]
  140.         [(= x (entry st)) st]
  141.         [(< x (entry st))
  142.          (make-tree (entry st)
  143.                     (tree-adjoin-set x (left-branch st))
  144.                     (right-branch st))]
  145.         [else (make-tree (entry st)
  146.                          (left-branch st)
  147.                          (tree-adjoin-set x (right-branch st)))]))
  148.  
  149. ;; two ways to convert a bst into a list
  150.  
  151. (define (tree->list1 tree)
  152.   (if (empty? tree)
  153.     empty
  154.     (append (tree->list1 (left-branch tree))
  155.             (cons (entry tree)
  156.                   (tree->list1 (right-branch tree))))))
  157.  
  158. (define (tree->list2 tree)
  159.   (define (copy-to-list tree result-list)
  160.     (if (empty? tree)
  161.       result-list
  162.       (copy-to-list (left-branch tree)
  163.                     (cons (entry tree)
  164.                           (copy-to-list (right-branch tree)
  165.                                         result-list)))))
  166.   (copy-to-list tree empty))
  167.  
  168. (define tree-2-16-1 (make-tree 7
  169.                                (make-tree 3
  170.                                           (list 1 empty empty)
  171.                                           (list 5 empty empty))
  172.                                (make-tree 9
  173.                                           empty
  174.                                           (list 11 empty empty))))
  175. (define tree-2-16-2 (make-tree 3
  176.                                (list 1 empty empty)
  177.                                (make-tree 7
  178.                                           (list 5 empty empty)
  179.                                           (make-tree 9
  180.                                                     empty
  181.                                                      (list 11 empty empty)))))
  182. (define tree-2-16-3 (make-tree 5
  183.                                (make-tree 3
  184.                                           (list 1 empty empty)
  185.                                           empty)
  186.                                (make-tree 9
  187.                                           (list 7 empty empty)
  188.                                           (list 11 empty empty))))
  189.  
  190. (displayln tree-2-16-1)
  191. ;; (7 (3 (1 () ()) (5 () ())) (9 () (11 () ())))
  192. (tree->list1 tree-2-16-1)
  193. ;; '(1 3 5 7 9 11)
  194. (tree->list2 tree-2-16-1)
  195. ;; '(1 3 5 7 9 11)
  196.  
  197. (displayln tree-2-16-2)
  198. ;; (3 (1 () ()) (7 (5 () ()) (9 () (11 () ()))))
  199. (tree->list1 tree-2-16-2)
  200. ;; '(1 3 5 7 9 11)
  201. (tree->list2 tree-2-16-2)
  202. ;; '(1 3 5 7 9 11)
  203.  
  204. (displayln tree-2-16-3)
  205. ;; (5 (3 (1 () ()) ()) (9 (7 () ()) (11 () ())))
  206. (tree->list1 tree-2-16-3)
  207. ;; '(1 3 5 7 9 11)
  208. (tree->list2 tree-2-16-3)
  209. ;; '(1 3 5 7 9 11)
  210.  
  211. ;; a.  The two procedures do produce the same result for every tree.  Both produce
  212. ;; a left traversal of the tree.
  213.  
  214. ;; b.  Both trees make two recursive calls on subproblems of about half-size, but
  215. ;; tree->list2 does constant work outside the recursion while tree->list1 does
  216. ;; linear work outside the recursion because of the call to append.  So
  217. ;; tree->list2 should be O(n), and tree->list1 should be O(n log n).
  218.  
  219. ;;;;;;;;;;
  220. ;; 2.64 ;;
  221. ;;;;;;;;;;
  222.  
  223. (define (list->tree elements)
  224.   (first (partial-tree elements (length elements))))
  225. (define (partial-tree elts n)
  226.   (cond [(zero? n) (cons empty elts)]
  227.         [else
  228.           (define left-size (quotient (sub1 n) 2))
  229.           (define left-result (partial-tree elts left-size))
  230.           (define left-tree (first left-result))
  231.           (define non-left-elts (rest left-result))
  232.           (define right-size (- n (add1 left-size)))
  233.           (define this-entry (first non-left-elts))
  234.           (define right-result (partial-tree (rest non-left-elts) right-size))
  235.           (define right-tree (first right-result))
  236.           (define remaining-elts (rest right-result))
  237.           (cons (make-tree this-entry left-tree right-tree)
  238.                 remaining-elts)]))
  239.  
  240. ;; a.  partial-tree takes an ordered list and a number, and returns a list
  241. ;; containing: a balanced binary tree consisting of the first number elements of
  242. ;; the ordered list, and the remaining unused elements.  The procedure works by
  243. ;; splitting the requisite number of elements into a triple of smaller numbers, a
  244. ;; middle number, and bigger numbers, recursively sending off the smaller and
  245. ;; bigger numbers to be made into trees, then using those trees as branches to
  246. ;; create the top-level tree having the middle element as entry.
  247.  
  248. (partial-tree '(1 2 3 4) 0)
  249. ;; '(() 1 2 3 4)
  250. (partial-tree '(1 2 3 4) 1)
  251. ;; '((1 () ()) 2 3 4)
  252. (partial-tree '(1 2 3 4) 2)
  253. ;; '((1 () (2 () ())) 3 4)
  254. (partial-tree '(1 2 3 4) 3)
  255. ;; '((2 (1 () ()) (3 () ())) 4)
  256. (partial-tree '(1 2 3 4) 4)
  257. ;; '((2 (1 () ()) (3 () (4 () ()))))
  258.  
  259. (list->tree '(1 3 5 7 9 11))
  260. ;; '(5 (1 () (3 () ())) (9 (7 () ()) (11 () ())))
  261.  
  262.     ;; 5
  263.   ;; /   \
  264.  ;; 1     9
  265. ;; / \   / \
  266.    ;; 3 7  11
  267.  
  268. ;; b.  partial-tree does constant work outside the recursion and makes two
  269. ;; recursive calls, each on a subproblem of about half size.  So the recursion
  270. ;; tree has n nodes and thus partial-tree runs in linear time.
  271.  
  272. ;;;;;;;;;;
  273. ;; 2.65 ;;
  274. ;;;;;;;;;;
  275.  
  276. ;; We can get linear time union-set and intersection-set for our tree
  277. ;; representation of sets by:  taking a tree, converting it into an ordered list
  278. ;; in linear time using tree->list2, then using the linear time operations we have
  279. ;; for sets as ordered lists, then converting back into trees, again in linear
  280. ;; time, using list->tree.
  281.  
  282. (define (tree-union-set t1 t2)
  283.   (define l1 (tree->list2 t1))
  284.   (define l2 (tree->list2 t2))
  285.   (define list-result (ordered-union-set l1 l2))
  286.   (list->tree list-result))
  287.  
  288. (define (tree-intersection-set t1 t2)
  289.   (define l1 (tree->list2 t1))
  290.   (define l2 (tree->list2 t2))
  291.   (define list-result (ordered-intersection-set l1 l2))
  292.   (list->tree list-result))
  293.  
  294. (define t1 (make-tree 3
  295.                       (list 1 empty empty)
  296.                       (make-tree 7
  297.                                  (list 5 empty empty)
  298.                                  (make-tree 9
  299.                                             empty
  300.                                             (list 11 empty empty)))))
  301. (tree->list2 t1)
  302. ;; '(1 3 5 7 9 11)
  303.  
  304. (define t2 (make-tree 5
  305.                       (make-tree 2
  306.                                  (list 1 empty empty)
  307.                                 empty)
  308.                       (make-tree 8
  309.                                  (list 7 empty empty)
  310.                                  (list 11 empty empty))))
  311. (tree->list2 t2)
  312. ;; '(1 2 5 7 8 11)
  313.  
  314. (tree-union-set t1 t2)
  315. ;; '(5 (2 (1 () ()) (3 () ())) (8 (7 () ()) (9 () (11 () ()))))
  316. (tree->list2 (tree-union-set t1 t2))
  317. ;; '(1 2 3 5 7 8 9 11)
  318.  
  319. (tree-intersection-set t1 t2)
  320. ;; '(5 (1 () ()) (7 () (11 () ())))
  321. (tree->list2 (tree-intersection-set t1 t2))
  322. ;; '(1 5 7 11)
  323.  
  324. ;;;;;;;;;;
  325. ;; 2.66 ;;
  326. ;;;;;;;;;;
  327.  
  328. (define (tree-lookup given-key set-of-records)
  329.   (cond [(empty? set-of-records) #f]
  330.         [(= given-key (entry set-of-records))
  331.          (entry set-of-records)]
  332.         [(< given-key (entry set-of-records))
  333.          (tree-lookup given-key (left-branch set-of-records))]
  334.         [else (tree-lookup given-key (right-branch set-of-records))]))
  335.  
  336. (displayln t1)
  337. ;; (3 (1 () ()) (7 (5 () ()) (9 () (11 () ()))))
  338. (tree-lookup 9 t1)
  339. ;; 9
  340. (tree-lookup 8 t1)
  341. ;; #f
Add Comment
Please, Sign In to add comment