;; set.sx — Phase 12 Data.Set: wraps Data.Map with unit values.
;;
;; A Set is a Map from key to (). All set operations delegate to the map
;; ops, ignoring the value side. Storage representation matches Data.Map:
;;
;;   Empty → ("Map-Empty")
;;   Node  → ("Map-Node" key () left right size)
;;
;; Tradeoff: trivial maintenance burden, slight overhead per node from
;; the unused value slot. Faster path forward than re-implementing the
;; weight-balanced BST.
;;
;; Functions live in this file; the Haskell-level `import Data.Set` /
;; `import qualified Data.Set as Set` wiring (next Phase 12 box) binds
;; them under the chosen alias.

(define hk-set-unit (list "Tuple"))

(define hk-set-empty hk-map-empty)

(define hk-set-singleton (fn (k) (hk-map-singleton k hk-set-unit)))

(define hk-set-insert (fn (k s) (hk-map-insert k hk-set-unit s)))

(define hk-set-delete hk-map-delete)
(define hk-set-member hk-map-member)
(define hk-set-size hk-map-size)
(define hk-set-null hk-map-null)
(define hk-set-to-asc-list hk-map-keys)
(define hk-set-to-list hk-map-keys)

(define
  hk-set-from-list
  (fn (xs) (reduce (fn (acc k) (hk-set-insert k acc)) hk-set-empty xs)))

(define
  hk-set-union
  (fn (a b) (hk-map-union-with (fn (x y) hk-set-unit) a b)))

(define
  hk-set-intersection
  (fn (a b) (hk-map-intersection-with (fn (x y) hk-set-unit) a b)))

(define hk-set-difference hk-map-difference)

(define
  hk-set-is-subset-of
  (fn (a b) (= (hk-map-size (hk-map-difference a b)) 0)))

(define
  hk-set-filter
  (fn (p s) (hk-map-filter-with-key (fn (k v) (p k)) s)))

(define hk-set-map (fn (f s) (hk-set-from-list (map f (hk-map-keys s)))))

(define
  hk-set-foldr
  (fn (f z s) (hk-map-foldr-with-key (fn (k v acc) (f k acc)) z s)))

(define
  hk-set-foldl
  (fn (f z s) (hk-map-foldl-with-key (fn (acc k v) (f acc k)) z s)))
