{-# LANGUAGE GeneralizedNewtypeDeriving #-}
module ELynx.Data.Tree.Subset
( Subset ()
, sfromset
, sfromlist
, smap
, snull
, sempty
, ssingleton
, sunion
, sunions
, sdifference
, sintersection
, sdisjoint
, smember
, sshow
) where
import Data.List (intercalate)
import qualified Data.Set as S
newtype Subset a = SS {subset :: S.Set a}
deriving (Show, Read, Eq, Ord, Semigroup, Monoid, Foldable)
sfromset :: S.Set a -> Subset a
sfromset = SS
sfromlist :: Ord a => [a] -> Subset a
sfromlist l = if S.size s == length l
then sfromset s
else error "pfromlist: List contains duplicate elements."
where s = S.fromList l
smap :: Ord b => (a -> b) -> Subset a -> Subset b
smap f = SS . S.map f . subset
snull :: Subset a -> Bool
snull = S.null . subset
sempty :: Subset a
sempty = SS S.empty
ssingleton :: a -> Subset a
ssingleton = SS . S.singleton
sunion :: Ord a => Subset a -> Subset a -> Subset a
sunion p q = SS $ subset q `S.union` subset p
sunions :: Ord a => [Subset a] -> Subset a
sunions = SS . S.unions . map subset
sdifference :: Ord a => Subset a -> Subset a -> Subset a
sdifference p q = SS $ subset p S.\\ subset q
sintersection :: Ord a => Subset a -> Subset a -> Subset a
sintersection p q = SS $ S.intersection (subset p) (subset q)
sdisjoint :: Ord a => Subset a -> Subset a -> Bool
sdisjoint p q = S.disjoint (subset p) (subset q)
smember :: Ord a => a -> Subset a -> Bool
smember x = S.member x . subset
sshow :: (a -> String) -> Subset a -> String
sshow f = intercalate "," . map f . S.toList . subset