This code is in the public domain. Do whatever you want with it. Eric Kow 2006-08-16 This is a library for dealing with optional command line arguments. Note: you probably want to have a cpp macro that looks a little like this: #define FLAG(x,y) data x = x y deriving (Eq, Show, Typeable) Some examples: ------------8<----------------------------------------------------------- {-# OPTIONS_GHC -fglasgow-exts #-} import Data.Typeable import FlagsAndSwitches data LogFileFlag = LogFileFlag String deriving (Eq, Show, Typeable) data TimeoutFlag = TimeoutFlag Int deriving (Eq, Show, Typeable) lf = Flag LogFileFlag "hi" tf = Flag TimeoutFlag 3 ------------8<----------------------------------------------------------- *Main> hasFlag LogFileFlag [ tf ] False *Main> hasFlag LogFileFlag [ lf, tf ] True *Main> [lf, tf] [Flag LogFileFlag "hi",Flag TimeoutFlag 3] *Main> setFlag LogFileFlag "bar" [ lf, tf ] [Flag LogFileFlag "bar",Flag TimeoutFlag 3] *Main> getFlag LogFileFlag [lf,tf] Just "bar" > {-# OPTIONS_GHC -fglasgow-exts #-} > module FlagsAndSwitches where > > import Data.List (find) > import Data.Typeable (Typeable, cast, typeOf) > > data Flag = forall f x . (Show f, Show x, Typeable f, Typeable x) => Flag (x -> f) x deriving Typeable > > instance Show Flag where > show (Flag f x) = "Flag " ++ show (f x) > isFlag :: (Typeable f, Typeable x) => (x -> f) -> Flag -> Bool > hasFlag :: (Typeable f, Typeable x) => (x -> f) -> [Flag] -> Bool > deleteFlag :: (Typeable f, Typeable x) => (x -> f) -> [Flag] -> [Flag] > setFlag :: (Show f, Show x, Typeable f, Typeable x) => (x -> f) -> x -> [Flag] -> [Flag] > getFlag :: (Show f, Show x, Typeable f, Typeable x) => (x -> f) -> [Flag] -> Maybe x > > isFlag f1 (Flag f2 _) = typeOf f1 == typeOf f2 > hasFlag f = any (isFlag f) > deleteFlag f = filter (not.isFlag f) > setFlag f v fs = (Flag f v) : tl where tl = deleteFlag f fs > getFlag f fs = find (isFlag f) fs >>= cast