Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to read three consecutive integers from stdin in Haskell?

I want to read an input like 12 34 56 into three integers using Haskell.

For a single integer, one might use myInteger <- readLn. But for this case, I have not found any solution, except the one of first reading a line, then replacing all spaces with ,, (using something like:

spaceToCommas str =
  let repl ' ' = ','
      repl  c =   c
  in map repl str

) and then calling read '[' ++ str ++ ']' which feels very hackish. Also, it does not allow me to state that I want to read three integers, it will attempt to read any amount of integers from stdin.

There has to be a better way.

Note that I would like a solution that does not rely on external packages. Using e.g. Parsec is of course great, but this simple example should not require the use of a full-fledged Parser Combinator framework, right?

like image 679
Qqwy Avatar asked Dec 31 '25 00:12

Qqwy


1 Answers

What about converting the string like:

convert :: Read a => String -> [a]
convert = map read . words

words splits the given string into a list of strings (the "words") and then we perform a read on every element using map.

and for instance use it like:

main = do
    line <- getLine
    let [a,b,c] = convert line :: [Int] in putStrLn (show (c,a,b))

or if you for instance want to read the first three elements and don't care about the rest (yes this apparently requires super-creativity skills):

main = do
    line <- getLine
    let (a:b:c:_) = convert line :: [Int] in putStrLn (show (c,a,b))

I here returned a tuple that is rotated one place to the right to show parsing is done.

like image 150
Willem Van Onsem Avatar answered Jan 02 '26 21:01

Willem Van Onsem



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!