Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- module Parser where
- import Text.ParserCombinators.Parsec
- import AccTree
- type BasicProgram = [BasicLine]
- data BasicLine = BasicLine
- { lineNumber :: Integer
- , command :: BasicCommand
- } deriving (Show)
- data BasicCommand
- = BasicLet String BasicExpr
- | BasicIf { condition :: BasicExpr, thenCmd :: BasicCommand, elseCmd :: Maybe BasicCommand }
- | BasicPrint BasicExpr
- deriving (Show)
- data BasicExpr
- = BinaryExpr BasicExpr BinOperator BasicExpr
- | UnaryExpr BasicExpr UnaryOperator
- | Var String
- | Literal Int
- deriving (Show)
- type BinOperator = String
- type UnaryOperator = String
- basicProgram :: GenParser Char st BasicProgram
- basicProgram = do
- result <- many basicLine
- ws
- optional $ string "END"
- eof
- return result
- basicLine :: GenParser Char st BasicLine
- basicLine = do
- lineNumber <- read <$> many1 digit
- ws
- command <- basicCommand
- ws
- return $ BasicLine lineNumber command
- basicCommand :: GenParser Char st BasicCommand
- basicCommand = basicLet
- basicLet :: GenParser Char st BasicCommand
- basicLet = do
- optional $ string "LET" >> ws
- id <- varName
- ws; char '='; ws
- expr <- expression
- return $ BasicLet id expr
- varName :: GenParser Char st [Char]
- varName = do
- firstChar <- choice [letter, char '_']
- otherChars <- many (choice [alphaNum , char '_'])
- return $ firstChar : otherChars
- expression :: GenParser Char st BasicExpr
- expression
- = literal
- <|> Var <$> varName
- literal :: GenParser Char st BasicExpr
- literal = Literal . read <$> many1 digit
- -- The end of line character is \n
- eol :: GenParser Char st Char
- eol = char '\n'
- ws :: GenParser Char st ()
- ws = optional $ choice $ comment : map char [' ', '\t', '\n']
- comment :: GenParser Char st Char
- comment = string "REM" >> many (noneOf ['\n']) >> eol
- parseBasic :: String -> Either ParseError BasicProgram
- parseBasic = parse basicProgram ""
- parseFile :: FilePath -> IO (Either ParseError BasicProgram)
- parseFile file = do
- file <- readFile file
- return $ parseBasic file
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement