I am trying to read a file into a function to calculate the frequencies of characters in a file. So I am trying the following:
charCount :: String -> [(Char, Int)]
charCount input = M.toList $ M.fromListWith (+) [(c, 1) | c <- input]
calculate :: FilePath -> [(Char, Int)]
calculate fp = do
c <- readFile fp
charCount c
But I am getting the following error:
FileWriter.hs:13:8: Couldn't match expected type ‘[String]’ …
with actual type ‘IO String’
In a stmt of a 'do' block: c <- readFile fp
In the expression:
do { c <- readFile fp;
charCount c }
Compilation failed.
Since calculate
calls the readFile
function which returns a value wrapped in the IO
monad the function calculate
must return a IO
value too, and the result of the call to charCount
(a pure computation) has to be return
ed in order to wrap the [(Char, Int)]
into a monad.
The next example worked in ghc 7.10.1
:
import qualified Data.Map as M
charCount :: String -> [(Char, Int)]
charCount input = M.toList $ M.fromListWith (+) [(c, 1) | c <- input]
calculate :: FilePath -> IO [(Char, Int)]
calculate fp =
readFile fp >>= \c ->
return (charCount c)