简体   繁体   中英

Reading lines and reversing the text with Haskell

My program should do the following:

  • Read lines from a file
  • For each line, reverse the text of each word ("bat cat hat" becomes "tab tac tah")
  • Print out the the reverse text

But it doesn't work and being a Haskell-newbie, I can't understand the errors.

Here is my code:

main = do
    content <- readFile "test.txt"
    let linesList = lines content
    reverseLines

reverseWords :: String -> String
reverseWords = unwords . map reverse . words

reverseLines :: [String] -> IO ()
reverseLines inputList = do
    if null inputList
        then return ()
        else do
        line <- inputList!!0
        if null line
            then return ()
            else do
                putStrLn $ reverseWords line
                reverseLines . tail inputList

And my errors:

readlines.hs:4:9:
    Couldn't match expected type `IO b0'
                with actual type `[String] -> IO ()'
    In a stmt of a 'do' block: reverseLines
    In the expression:
      do { content <- readFile "test.txt";
           let linesList = lines content;
           reverseLines }
    In an equation for `main':
        main
          = do { content <- readFile "test.txt";
                 let linesList = ...;
                 reverseLines }

readlines.hs:14:25:
    Couldn't match type `[Char]' with `IO [Char]'
    Expected type: [IO [Char]]
      Actual type: [String]
    In the first argument of `(!!)', namely `inputList'
    In a stmt of a 'do' block: line <- inputList !! 0
    In the expression:
      do { line <- inputList !! 0;
           if null line then
               return ()
           else
               do { putStrLn $ reverseWords line;
                    .... } }

readlines.hs:19:33:
    Couldn't match expected type `IO ()' with actual type `a0 -> IO ()'
    In a stmt of a 'do' block: reverseLines . tail inputList
    In the expression:
      do { putStrLn $ reverseWords line;
           reverseLines . tail inputList }
    In a stmt of a 'do' block:
      if null line then
          return ()
      else
          do { putStrLn $ reverseWords line;
               reverseLines . tail inputList }

readlines.hs:19:48:
    Couldn't match expected type `a0 -> [String]'
                with actual type `[String]'
    In the return type of a call of `tail'
    Probable cause: `tail' is applied to too many arguments
    In the second argument of `(.)', namely `tail inputList'
    In a stmt of a 'do' block: reverseLines . tail inputList

Firstly, your last line in your main function is of type [String] -> IO (), and you need it to be IO (), so you actually need to pass it the list of strings. Here is one way to do what you are requesting:

main :: IO ()
main = do
    content <- readFile "test.txt"
    let linesList = lines content
    reverseLines linesList

reverseWords :: String -> String
reverseWords = unwords . map reverse . words

reverseLines :: [String] -> IO ()
reverseLines = mapM_ (putStrLn . reverseWords)

And here is a recursive version akin to what you wanted to do in your version

reverseLines2 :: [String] -> IO ()
reverseLines2 []      = return ()
reverseLines2 (x:xs)  = do
  putStrLn (reverseWords x)
  reverseLines2 xs

I've also fixed your version with minimal changes, but bear in mind that this is not really the Haskell way to do things. Go with one of the options I provided above.

main = do
    content <- readFile "test.txt"
    let linesList = lines content
    reverseLines linesList

reverseWords :: String -> String
reverseWords = unwords . map reverse . words

reverseLines :: [String] -> IO ()
reverseLines inputList = do
    if null inputList
        then return ()
    else do
      let line = head inputList 
      if null line
          then return ()
          else do
              putStrLn $ reverseWords line
              reverseLines $ tail inputList

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM