content: {-# LANGUAGE TypeSynonymInstances #-}
  {-# LANGUAGE FlexibleInstances #-}
  
  module Unused.Util
      ( groupBy
      , stringToInt
      , safeHead
      , safeReadFile
      ) where
  
  import Control.Arrow ((&&&))
  import qualified Control.Exception as E
  import qualified Data.ByteString.Char8 as C8
  import qualified Data.ByteString.Lazy.Char8 as Cl8
  import qualified Data.Char as C
  import Data.Function (on)
  import qualified Data.List as L
  
  groupBy :: (Ord b) => (a -> b) -> [a] -> [(b, [a])]
  groupBy f = map (f . head &&& id) . L.groupBy ((==) `on` f) . L.sortBy (compare `on` f)
  
  safeHead :: [a] -> Maybe a
  safeHead (x:_) = Just x
  safeHead _ = Nothing
  
  stringToInt :: String -> Maybe Int
  stringToInt xs
      | all C.isDigit xs = Just $ loop 0 xs
      | otherwise = Nothing
    where
      loop = foldl (\acc x -> acc * 10 + C.digitToInt x)
  
  class Readable a where
      readFile' :: FilePath -> IO a
  
  instance Readable String where
      readFile' = readFile
  
  instance Readable C8.ByteString where
      readFile' = C8.readFile
  
  instance Readable Cl8.ByteString where
      readFile' = Cl8.readFile
  
  safeReadFile :: Readable s => FilePath -> IO (Either E.IOException s)
  safeReadFile = E.try . readFile'
  