Advertisement
Guest User

Untitled

a guest
Dec 13th, 2017
83
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 0.93 KB | None | 0 0
  1. import Control.Monad.Except
  2. import Data.Char
  3. data ParseError = ParseError {location::Int, reason::String}
  4.  
  5. type ParseMonad = Either ParseError
  6.  
  7. parseDig :: Char -> Integer -> ParseMonad Integer
  8. parseDig x pos = do
  9. if isHexDigit x
  10. then return $ toInteger $ digitToInt x
  11. else throwError $ ParseError (fromInteger pos) (x:": Invalid digit")
  12.  
  13.  
  14.  
  15.  
  16. parseHex' :: String -> Integer -> Integer -> ParseMonad Integer
  17. parseHex' [x] pos acc = do
  18. b <- (parseDig x pos)
  19. return $ acc * 16 + b
  20.  
  21.  
  22. parseHex' (x:xs) pos acc = do
  23. b <- parseDig x pos
  24. c <- parseHex' xs (pos + 1) (acc * 16 + b)
  25. return c
  26.  
  27.  
  28. parseHex :: String -> ParseMonad Integer
  29. parseHex x = parseHex' x 1 1
  30.  
  31. printError :: ParseError -> ParseMonad String
  32. printError pe = Right $ "At pos " ++ (show (location pe)) ++ ": " ++ (reason pe)
  33.  
  34. test s = str where
  35. (Right str) = do
  36. n <- parseHex s
  37. return $ show n
  38. `catchError` printError
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement