Pastebin launched a little side project called VERYVIRAL.com, check it out ;-) Want more features on Pastebin? Sign Up, it's FREE!
Guest

Haskell lazy I/O and closing files 3

By: a guest on Jun 5th, 2010  |  syntax: Haskell  |  size: 1.16 KB  |  views: 190  |  expires: Never
download  |  raw  |  embed  |  report abuse  |  print
Text below is selected. Please press Ctrl+C to copy to your clipboard. (⌘+C on Mac)
  1. import Control.Monad
  2. import Data.Digest.MD5 (hash)
  3. import Data.Word
  4. import List (sort)
  5. import Prelude
  6. import System.Directory
  7. import System.FilePath
  8. import Text.Printf (printf)
  9. import qualified Data.ByteString as BS
  10.  
  11. main :: IO ()
  12.  
  13. main = putStr . unlines =<< getList "."
  14.  
  15. getList :: FilePath -> IO [String]
  16.  
  17. getList p = mapM getFileLine =<< getRecursiveContents p
  18.     where
  19.         getFileLine path = liftM
  20.                 (\c -> (hex (hash (BS.unpack c))) ++ " " ++ path)
  21.                 (BS.readFile path)
  22.  
  23. hex :: [Word8] -> String
  24.  
  25. hex = concatMap (\x -> printf "%0.2x" (toInteger x))
  26.  
  27. getRecursiveContents :: FilePath -> IO [FilePath]
  28.  
  29. getRecursiveContents topdir = do
  30.         names <- getDirectoryContents topdir
  31.  
  32.         let properNames = filter (`notElem` [".", ".."]) names
  33.  
  34.         paths <- concatForM properNames $ \name -> do
  35.                 let path = topdir </> name
  36.  
  37.                 isDirectory <- doesDirectoryExist path
  38.                 if isDirectory
  39.                         then getRecursiveContents path
  40.                         else do
  41.                                 isFile <- doesFileExist path
  42.                                 if isFile
  43.                                         then return [path]
  44.                                         else return []
  45.  
  46.         return (sort paths)
  47.  
  48. concatForM :: (Monad m) => [a1] -> (a1 -> m [a]) -> m [a]
  49.  
  50. concatForM xs f = liftM concat (forM xs f)