Search code examples
haskellparsecrecursive-datastructuresattoparsec

Parse recursive data with parsec


import Data.Attoparsec.Text.Lazy
import Data.Text.Lazy.Internal (Text)
import Data.Text.Lazy (pack)

data List a = Nil | Cons a (List a)

list :: Text
list = pack $ unlines
  [ "0"
  , "1"
  , "2"
  , "5"
  ]

How can List Int parser coud be implemented to parse Cons 0 (Cons 1 (Cons 2 (Cons 5 Nil))) from list?

ps: pure parser without parsing a [Int] and converting it to List Int is preferable.


Solution

  • Like this:

    import Control.Applicative
    -- rest of imports as in question
    
    data List a = Nil | Cons a (List a)
      deriving Show -- for testing
    
    -- definition of list as in question
    
    parseList :: Parser (List Int)
    parseList = foldr Cons Nil <$> many (decimal <* endOfLine)
    

    Testing in GHCi:

    *Main> parse parseList list
    Done "" Cons 0 (Cons 1 (Cons 2 (Cons 5 Nil)))