;;;; Copyright 2002, Jonathan Bachrach.  See file TERMS.

(use goo/boot)
(use goo/macros)
(use goo/types)
(use goo/math)
(use goo/cols/col)
(use goo/cols/map)
(use goo/cols/seq)
(use goo/cols/lst)

;; 3.7.2.1 ASSOCIATIONS

;;;;!! Interface
(exported
 (dc <assocs> (<map> <col!>))
   (dp assocs-test (<assocs> => <fun>) ==)
)

;;;;!! Implementation
  (dp assocs-keys (<assocs> => <lst>) '())
  (dp assocs-vals (<assocs> => <lst>) '())

;;;; Collection protocol
(dm len (x|<assocs> => <int>)
  (len (assocs-keys x)))

(dm elt-or (x|<assocs> key default => <any>)
  (rep fnd ((keys|<lst> (assocs-keys x)) (vals|<lst> (assocs-vals x)))
    (if (== keys '())
        default
        (if ((assocs-test x) key (head keys))
            (head vals)
            (fnd (tail keys) (tail vals))))))

(dm elt-setter (val x|<assocs> key)
  (rep fnd ((keys|<lst> (assocs-keys x)) (vals|<lst> (assocs-vals x)))
    (if (== keys '())
        (seq (set (assocs-keys x) (pair key (assocs-keys x)))
             (set (assocs-vals x) (pair val (assocs-vals x)))
          val)
        (if ((assocs-test x) key (head keys))
            (set (head vals) val)
            (fnd (tail keys) (tail vals))))))

(dm fab ((c (t= <assocs>)) s|<int> => <assocs>)
  (new <assocs>))