Say I have
import qualified Data.List as L
data MyData = Foo Int | Bar Char | Baz String
deriving (Eq, Show, Ord)
list :: [MyData]
list = [Foo 1, Bar 'c', Baz "palla", Bar 'd', Foo 8]
I would like to group list
by constructors, like this
-- [[Foo 1, Foo 8], [Bar 'c', Bar 'd'], [Baz "palla"]]
-- to feed to something like printGroup :: [MyData] -> IO ()
The naive implementation is:
groupByConstructor :: [MyData] -> [[MyData]]
groupByConstructor ds = L.groupBy isSameConst (L.sort ds)
where
isSameConst :: MyData -> MyData -> Bool
isSameConst (Foo _) (Foo _) = True
isSameConst (Bar _) (Bar _) = True
isSameConst (Baz _) (Baz _) = True
isSameConst _ _ = False
main :: IO ()
main = print $ groupByConstructor list
-- [[Foo 1,Foo 8],[Bar 'c',Bar 'd'],[Baz "palla"]]
which works. But has a big problem in my case: if I add constructors to MyData
-Wall
won’t warning about incomplete pattern matches in isSameConst
, which I would really like.
Is there a better way to solve this problem?