(.module: [lux #* [control [equivalence (#+ Equivalence)] ["." hash (#+ Hash)] [predicate (#+ Predicate)]] [data [collection ["dict" dictionary (#+ Dictionary)] ["." list ("list/." Fold)]]] [type abstract]]) (abstract: #export (Set a) {} (Dictionary a a) (def: #export new (All [a] (-> (Hash a) (Set a))) (|>> dict.new :abstraction)) (def: #export size (All [a] (-> (Set a) Nat)) (|>> :representation dict.size)) (def: #export (add elem set) (All [a] (-> a (Set a) (Set a))) (|> set :representation (dict.put elem elem) :abstraction)) (def: #export (remove elem set) (All [a] (-> a (Set a) (Set a))) (|> set :representation (dict.remove elem) :abstraction)) (def: #export (member? set elem) (All [a] (-> (Set a) a Bit)) (|> set :representation (dict.contains? elem))) (def: #export to-list (All [a] (-> (Set a) (List a))) (|>> :representation dict.keys)) (def: #export (union xs yx) (All [a] (-> (Set a) (Set a) (Set a))) (:abstraction (dict.merge (:representation xs) (:representation yx)))) (def: #export (difference sub base) (All [a] (-> (Set a) (Set a) (Set a))) (list/fold ..remove base (..to-list sub))) (def: #export (intersection filter base) (All [a] (-> (Set a) (Set a) (Set a))) (:abstraction (dict.select (dict.keys (:representation filter)) (:representation base)))) (structure: #export Equivalence (All [a] (Equivalence (Set a))) (def: (= reference sample) (let [[Hash _] (:representation reference)] (:: (list.Equivalence (get@ #hash.eq Hash)) = (..to-list reference) (..to-list sample))))) (structure: #export Hash (All [a] (Hash (Set a))) (def: eq ..Equivalence) (def: (hash set) (let [[Hash _] (:representation set)] (list/fold (function (_ elem acc) (n/+ (:: Hash hash elem) acc)) 0 (..to-list set))))) ) (def: #export empty? (All [a] (-> (Set a) Bit)) (|>> ..size (n/= 0))) (def: #export (from-list Hash xs) (All [a] (-> (Hash a) (List a) (Set a))) (list/fold ..add (..new Hash) xs)) (def: #export (sub? super sub) (All [a] (-> (Set a) (Set a) Bit)) (list.every? (..member? super) (..to-list sub))) (def: #export (super? sub super) (All [a] (-> (Set a) (Set a) Bit)) (sub? super sub)) (def: #export predicate (All [a] (-> (Set a) (Predicate a))) ..member?)