1

I get text from .txt, process it. I get vowels and their number from the text. I cannot write tuple list [(Char, Int)] to text file. I want to make each line to have a letter and its number, but I can't write it at all.

`

import Data.List
import Char

add :: Eq a => a -> [(a, Int)] -> [(a, Int)]
add x [] = [(x, 1)]
add x ((y, n):rest) = if x == y
    then (y, n+1) : rest
    else (y, n) : add x rest
 
count :: Eq a => [a] -> [(a, Int)]
count = sortBy f . foldr add [] where
    f (_, x) (_, y) = compare y x

ff x = filter (\x->elem (fst x) "aeyioAEYIO") x

fff x = ff (count x)

main :: IO ()
main = do
   src <- readFile "input.txt"
   writeFile "output.txt" (operate src)

operate :: [(Char, Int)] -> String
operate = fff

It gives out an error:

*** Term           : operate
*** Type           : [Char] -> [(Char,Int)]
*** Does not match : [(Char,Int)] -> String
  • Look what parameter you're passing to `operate`. What is its type? What does `operate`'s type signature say that the type should be? There's your mismatch. – Fyodor Soikin Dec 25 '22 at 01:19
  • Hint: `src :: String` and `fff :: String -> [(Char, Int)]`. – Joseph Sible-Reinstate Monica Dec 25 '22 at 04:17
  • @JosephSible-ReinstateMonica Thanks for the answer, but I don't quite understand what and where to change. I'm new to Haskell and don't fully understand everything. Could you be more specific, if you don't mind? – Clark Brown Dec 25 '22 at 10:41
  • @FyodorSoikin Thanks for the answer, but I don't quite understand what and where to change. I'm new to Haskell and don't fully understand everything. Could you be more specific, if you don't mind? – Clark Brown Dec 25 '22 at 10:41

1 Answers1

0

operate type is wrong because fff has type [Char] -> [(Char, Int)]

operate :: [(Char, Int)] -> String
operate = fff

type inferenece suggests [Char] -> [(Char, Int)],

good but return type still needs to be [(String, Int)] if we want to feed output of this function to formatOne

formatOne :: Show a => (String, a) -> String
formatOne (s, i) = s ++ " : " ++ show i

operate :: String -> [(String, Int)]
operate =  map (\(x,y) -> (x:"", y)) . fff
-- (\(x,y) -> (x:"", y)) this lambda turns first element of tuple from Char to String

-- unlines joins elements of list into string while separating elements with \n
formatAll = unlines . map formatOne

main :: IO ()
main = do
  src <- readFile "input.txt"
  writeFile "output.txt" (formatAll (operate src))
  • Thanks for the answer, but now I get another error because of `formatAll` `ERROR "":24 - Unresolved top-level overloading *** Binding : formatAll *** Outstanding context : Show b ` – Clark Brown Dec 25 '22 at 11:16
  • @ClarkBrown, hmm, try to inline it, like this `writeFile "output.txt" (unlines . map formatOne (operate src))` – Almaz Galiev Dec 25 '22 at 11:27
  • I tried it, but the same error((( Could it have something to do with what I have Haskell98? – Clark Brown Dec 25 '22 at 11:32