import Text.Read hiding ((+++))
import Text.ParserCombinators.ReadP
import Data.Char (isDigit)
data FruitType
= Apple
| Banana
deriving Show
instance Read FruitType where
readPrec = readP_to_Prec (const readFruitType)
readFruitType :: ReadP FruitType
readFruitType = (string "A" >> pure Apple)
+++ (string "B" >> pure Banana)
data FruitPack = FruitPack FruitType Int
deriving Show
instance Read FruitPack where
readPrec = readP_to_Prec (const readFruitPack)
readNumber :: ReadP Int
readNumber = do
i <- munch1 isDigit
pure $ read i
readFruitPack :: ReadP FruitPack
readFruitPack = do
skipSpaces
t <- readFruitType
skipSpaces
i <- readNumber
skipSpaces
eof
pure $ FruitPack t i
main :: IO ()
main = do
let as = read <$> [" A 10","B 300 "] :: [FruitPack]
print as
let bs = read "A 10 B 3 A 20 B 400" :: [FruitPack]
print bs
I can read
single FruitPack
, but How can I read chain of them (as in bs
) without having to split the string using <space>
as delimiter?
$ runhaskell read.hs
[FruitPack Apple 10,FruitPack Banana 300]
read.hs: Prelude.read: no parse