-- | Abstract Data Type Example: Efficient Queues -- Functional Programming course 2016. -- Thomas Hallgren module Queue(Q,empty,add,isEmpty,front,remove) where data Q a = Q [a] [a] deriving (Show) -- | An empty queue empty :: Q a empty = smartQ [] [] -- | Add an element at the back add :: a -> Q a -> Q a add x (Q fs bs) = smartQ fs (x:bs) -- | Check if the queue is empty isEmpty :: Q a -> Bool isEmpty (Q [] _) = True isEmpty _ = False -- | Inspect the front element front :: Q a -> a front (Q (x:fs) bs) = x -- | Remove an element from the front remove :: Q a -> Q a remove (Q (x:fs) bs) = smartQ fs bs -- Invariant: queue not empty => front list not empty -- A smart constructor smartQ [] bs = Q (reverse bs) [] smartQ fs bs = Q fs bs instance Eq a => Eq (Q a) where q1 == q2 = toList q1 == toList q2 toList (Q fs bs) = fs++reverse bs