module Data.Text.Parser
( Parser(..)
, Result(..)
, parseOnly
, char
, notChar
, anyChar
, satisfy
, space
, isSpace
, skipSpace
, peekChar
, string
, stringCI
, Data.Text.Parser.take
, scan
, runScanner
, Data.Text.Parser.takeWhile
, takeWhile1
, takeTill
, takeTill1
, signed
, decimal
, hexadecimal
, octal
, fractional
, provided
, choice
, Snack.Combinators.count
, optional
, eitherP
, option
, many
, many1
, manyTill
, sepBy
, sepBy1
, wrap
, match
, label
, extent
, takeText
, endOfInput
, atEnd
, Control.Applicative.empty
, pure
, guard
, when
, unless
, void
)
where
import Prelude hiding (null, length, splitAt, take)
import Control.Applicative
import Control.Monad
import Data.Char
import Data.Maybe
import Data.Text as T
import Data.Text.Unsafe as T
import Data.Text.Encoding as T
import Data.ByteString qualified as BS
import Data.ByteString.Lex.Fractional qualified as LF
import Data.ByteString.Lex.Integral qualified as LI
import Snack.Combinators
data Result a
= Success a {-# UNPACK #-} !Text
| Failure [String] {-# UNPACK #-} !Text
| Error String {-# UNPACK #-} !Text {-# UNPACK #-} !Int
deriving (Result a -> Result a -> Bool
(Result a -> Result a -> Bool)
-> (Result a -> Result a -> Bool) -> Eq (Result a)
forall a. Eq a => Result a -> Result a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: Result a -> Result a -> Bool
$c/= :: forall a. Eq a => Result a -> Result a -> Bool
== :: Result a -> Result a -> Bool
$c== :: forall a. Eq a => Result a -> Result a -> Bool
Eq, Int -> Result a -> ShowS
[Result a] -> ShowS
Result a -> String
(Int -> Result a -> ShowS)
-> (Result a -> String) -> ([Result a] -> ShowS) -> Show (Result a)
forall a. Show a => Int -> Result a -> ShowS
forall a. Show a => [Result a] -> ShowS
forall a. Show a => Result a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [Result a] -> ShowS
$cshowList :: forall a. Show a => [Result a] -> ShowS
show :: Result a -> String
$cshow :: forall a. Show a => Result a -> String
showsPrec :: Int -> Result a -> ShowS
$cshowsPrec :: forall a. Show a => Int -> Result a -> ShowS
Show)
instance Functor Result where
{-# INLINE fmap #-}
fmap :: forall a b. (a -> b) -> Result a -> Result b
fmap a -> b
fn (Success a
res Text
more) = b -> Text -> Result b
forall a. a -> Text -> Result a
Success (a -> b
fn a
res) Text
more
fmap a -> b
_ (Failure [String]
expected Text
more) = [String] -> Text -> Result b
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
fmap a -> b
_ (Error String
reason Text
more Int
len) = String -> Text -> Int -> Result b
forall a. String -> Text -> Int -> Result a
Error String
reason Text
more Int
len
newtype Parser a =
Parser
{ forall a. Parser a -> Text -> Result a
runParser :: Text -> Result a
}
instance Functor Parser where
{-# INLINE fmap #-}
fmap :: forall a b. (a -> b) -> Parser a -> Parser b
fmap a -> b
fn Parser{Text -> Result a
runParser :: Text -> Result a
runParser :: forall a. Parser a -> Text -> Result a
runParser} = (Text -> Result b) -> Parser b
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
(a -> b) -> Result a -> Result b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
fn (Text -> Result a
runParser Text
inp)
instance Applicative Parser where
{-# INLINE pure #-}
pure :: forall a. a -> Parser a
pure a
x = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
x Text
inp
{-# INLINE (<*>) #-}
(Parser Text -> Result (a -> b)
runFn) <*> :: forall a b. Parser (a -> b) -> Parser a -> Parser b
<*> (Parser Text -> Result a
runArg) = (Text -> Result b) -> Parser b
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Text -> Result (a -> b)
runFn Text
inp of
Success a -> b
fn Text
rest -> (a -> b) -> Result a -> Result b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
fn (Text -> Result a
runArg Text
rest)
Failure [String]
expected Text
more -> [String] -> Text -> Result b
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
Error String
reason Text
more Int
len -> String -> Text -> Int -> Result b
forall a. String -> Text -> Int -> Result a
Error String
reason Text
more Int
len
instance Alternative Parser where
{-# INLINE empty #-}
empty :: forall a. Parser a
empty = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [] Text
inp
{-# INLINE (<|>) #-}
(Parser Text -> Result a
runLeft) <|> :: forall a. Parser a -> Parser a -> Parser a
<|> (Parser Text -> Result a
runRight) = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Text -> Result a
runLeft Text
inp of
Success a
res Text
more -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Error String
reason Text
more Int
len -> String -> Text -> Int -> Result a
forall a. String -> Text -> Int -> Result a
Error String
reason Text
more Int
len
Failure [String]
expected Text
more ->
case Text -> Result a
runRight Text
inp of
Success a
res' Text
more' -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res' Text
more'
Error String
reason' Text
more' Int
len' -> String -> Text -> Int -> Result a
forall a. String -> Text -> Int -> Result a
Error String
reason' Text
more' Int
len'
Failure [String]
expected' Text
more' ->
case Text -> Int
length Text
more Int -> Int -> Ordering
forall a. Ord a => a -> a -> Ordering
`compare` Text -> Int
length Text
more' of
Ordering
LT -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
Ordering
EQ -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure ([String]
expected [String] -> [String] -> [String]
forall a. Semigroup a => a -> a -> a
<> [String]
expected') Text
more
Ordering
GT -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String]
expected' Text
more'
instance Monad Parser where
{-# INLINE (>>=) #-}
(Parser Text -> Result a
runLeft) >>= :: forall a b. Parser a -> (a -> Parser b) -> Parser b
>>= a -> Parser b
right = (Text -> Result b) -> Parser b
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Text -> Result a
runLeft Text
inp of
Success a
res Text
more -> Parser b -> Text -> Result b
forall a. Parser a -> Text -> Result a
runParser (a -> Parser b
right a
res) Text
more
Failure [String]
expected Text
more -> [String] -> Text -> Result b
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
Error String
reason Text
more Int
len -> String -> Text -> Int -> Result b
forall a. String -> Text -> Int -> Result a
Error String
reason Text
more Int
len
instance MonadPlus Parser
instance MonadFail Parser where
{-# INLINE CONLIKE fail #-}
fail :: forall a. String -> Parser a
fail String
reason = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> String -> Text -> Int -> Result a
forall a. String -> Text -> Int -> Result a
Error String
reason Text
inp Int
0
{-# INLINE CONLIKE char #-}
char :: Char -> Parser Char
char :: Char -> Parser Char
char Char
c = String -> Parser Char -> Parser Char
forall a. String -> Parser a -> Parser a
label (Char -> String
forall a. Show a => a -> String
show Char
c) (Parser Char -> Parser Char) -> Parser Char -> Parser Char
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> Parser Char
satisfy (Char
c Char -> Char -> Bool
forall a. Eq a => a -> a -> Bool
==)
{-# INLINE CONLIKE notChar #-}
notChar :: Char -> Parser Char
notChar :: Char -> Parser Char
notChar Char
c = (Char -> Bool) -> Parser Char
satisfy (Char
c Char -> Char -> Bool
forall a. Eq a => a -> a -> Bool
/=)
{-# INLINE CONLIKE parseOnly #-}
parseOnly :: Parser a -> Text -> Maybe a
parseOnly :: forall a. Parser a -> Text -> Maybe a
parseOnly Parser a
par = \Text
inp ->
case Parser a -> Text -> Result a
forall a. Parser a -> Text -> Result a
runParser Parser a
par Text
inp of
Success a
res Text
_ -> a -> Maybe a
forall a. a -> Maybe a
Just a
res
Result a
_otherwise -> Maybe a
forall a. Maybe a
Nothing
{-# INLINE anyChar #-}
anyChar :: Parser Char
anyChar :: Parser Char
anyChar = (Text -> Result Char) -> Parser Char
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
if Text -> Bool
null Text
inp
then [String] -> Text -> Result Char
forall a. [String] -> Text -> Result a
Failure [String
"any char"] Text
inp
else Char -> Text -> Result Char
forall a. a -> Text -> Result a
Success (Text -> Char
unsafeHead Text
inp) (Text -> Text
unsafeTail Text
inp)
{-# INLINE CONLIKE satisfy #-}
satisfy :: (Char -> Bool) -> Parser Char
satisfy :: (Char -> Bool) -> Parser Char
satisfy Char -> Bool
isOk = (Text -> Result Char) -> Parser Char
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
if Text -> Bool
null Text
inp
then [String] -> Text -> Result Char
forall a. [String] -> Text -> Result a
Failure [String
"more input"] Text
inp
else let c :: Char
c = Text -> Char
unsafeHead Text
inp
in if Char -> Bool
isOk Char
c
then Char -> Text -> Result Char
forall a. a -> Text -> Result a
Success Char
c (Text -> Text
unsafeTail Text
inp)
else [String] -> Text -> Result Char
forall a. [String] -> Text -> Result a
Failure [] Text
inp
{-# INLINE space #-}
space :: Parser Char
space :: Parser Char
space = String -> Parser Char -> Parser Char
forall a. String -> Parser a -> Parser a
label String
"space" (Parser Char -> Parser Char) -> Parser Char -> Parser Char
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> Parser Char
satisfy Char -> Bool
isSpace
{-# INLINE skipSpace #-}
skipSpace :: Parser ()
skipSpace :: Parser ()
skipSpace = Parser Text -> Parser ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (Parser Text -> Parser ()) -> Parser Text -> Parser ()
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> Parser Text
Data.Text.Parser.takeWhile Char -> Bool
isSpace
{-# INLINE peekChar #-}
peekChar :: Parser Char
peekChar :: Parser Char
peekChar = (Text -> Result Char) -> Parser Char
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
if Text -> Bool
null Text
inp
then [String] -> Text -> Result Char
forall a. [String] -> Text -> Result a
Failure [String
"more input"] Text
inp
else Char -> Text -> Result Char
forall a. a -> Text -> Result a
Success (Text -> Char
unsafeHead Text
inp) Text
inp
{-# INLINE CONLIKE string #-}
string :: Text -> Parser Text
string :: Text -> Parser Text
string Text
str = (Text -> Result Text) -> Parser Text
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
let (Text
pfx, Text
sfx) = Int -> Text -> (Text, Text)
splitAt (Text -> Int
length Text
str) Text
inp
in case Text
pfx Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
== Text
str of
Bool
True -> Text -> Text -> Result Text
forall a. a -> Text -> Result a
Success Text
pfx Text
sfx
Bool
False -> [String] -> Text -> Result Text
forall a. [String] -> Text -> Result a
Failure [Text -> String
forall a. Show a => a -> String
show Text
pfx] Text
inp
{-# INLINE CONLIKE stringCI #-}
stringCI :: Text -> Parser Text
stringCI :: Text -> Parser Text
stringCI Text
str = (Text -> Result Text) -> Parser Text
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
let (Text
pfx, Text
sfx) = Int -> Text -> (Text, Text)
splitAt (Text -> Int
length Text
str) Text
inp
in case Text -> Text
toCaseFold Text
pfx Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
== Text -> Text
toCaseFold Text
str of
Bool
True -> Text -> Text -> Result Text
forall a. a -> Text -> Result a
Success Text
pfx Text
sfx
Bool
False -> [String] -> Text -> Result Text
forall a. [String] -> Text -> Result a
Failure [Text -> String
forall a. Show a => a -> String
show Text
pfx] Text
inp
{-# INLINE CONLIKE take #-}
take :: Int -> Parser Text
take :: Int -> Parser Text
take Int
n = (Text -> Result Text) -> Parser Text
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
if Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
> Text -> Int
length Text
inp
then [String] -> Text -> Result Text
forall a. [String] -> Text -> Result a
Failure [Int -> String
forall a. Show a => a -> String
show Int
n String -> ShowS
forall a. Semigroup a => a -> a -> a
<> String
" more characters"] Text
inp
else let (Text
pfx, Text
more) = Int -> Text -> (Text, Text)
splitAt Int
n Text
inp
in Text -> Text -> Result Text
forall a. a -> Text -> Result a
Success Text
pfx Text
more
{-# INLINE CONLIKE scan #-}
scan :: s -> (s -> Char -> Maybe s) -> Parser Text
scan :: forall s. s -> (s -> Char -> Maybe s) -> Parser Text
scan s
state s -> Char -> Maybe s
scanner = (Text, s) -> Text
forall a b. (a, b) -> a
fst ((Text, s) -> Text) -> Parser (Text, s) -> Parser Text
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> s -> (s -> Char -> Maybe s) -> Parser (Text, s)
forall s. s -> (s -> Char -> Maybe s) -> Parser (Text, s)
runScanner s
state s -> Char -> Maybe s
scanner
{-# INLINE CONLIKE runScanner #-}
runScanner :: s -> (s -> Char -> Maybe s) -> Parser (Text, s)
runScanner :: forall s. s -> (s -> Char -> Maybe s) -> Parser (Text, s)
runScanner s
state s -> Char -> Maybe s
scanner = (Text -> Result (Text, s)) -> Parser (Text, s)
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> Text -> s -> Int -> Result (Text, s)
loop Text
inp s
state Int
0
where
loop :: Text -> s -> Int -> Result (Text, s)
loop Text
inp !s
st !Int
n =
case Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>= Text -> Int
lengthWord8 Text
inp of
Bool
True -> (Text, s) -> Text -> Result (Text, s)
forall a. a -> Text -> Result a
Success (Text
inp, s
st) Text
forall a. Monoid a => a
mempty
Bool
False ->
case Text -> Int -> Iter
iter Text
inp Int
n of
Iter Char
c Int
n' ->
case s -> Char -> Maybe s
scanner s
st Char
c of
Maybe s
Nothing -> (Text, s) -> Text -> Result (Text, s)
forall a. a -> Text -> Result a
Success (Int -> Text -> Text
takeWord8 Int
n Text
inp, s
st) (Int -> Text -> Text
dropWord8 Int
n Text
inp)
Just s
st' -> Text -> s -> Int -> Result (Text, s)
loop Text
inp s
st' (Int
n Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
n')
{-# INLINE CONLIKE takeWhile #-}
takeWhile :: (Char -> Bool) -> Parser Text
takeWhile :: (Char -> Bool) -> Parser Text
takeWhile Char -> Bool
test = (Char -> Bool) -> Parser Text
takeTill (Bool -> Bool
not (Bool -> Bool) -> (Char -> Bool) -> Char -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Char -> Bool
test)
{-# INLINE CONLIKE takeWhile1 #-}
takeWhile1 :: (Char -> Bool) -> Parser Text
takeWhile1 :: (Char -> Bool) -> Parser Text
takeWhile1 Char -> Bool
test = (Char -> Bool) -> Parser Text
Data.Text.Parser.takeWhile Char -> Bool
test Parser Text -> (Text -> Bool) -> Parser Text
forall (m :: * -> *) a.
(Alternative m, Monad m) =>
m a -> (a -> Bool) -> m a
`provided` (Bool -> Bool
not (Bool -> Bool) -> (Text -> Bool) -> Text -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Text -> Bool
null)
{-# INLINE CONLIKE takeTill #-}
takeTill :: (Char -> Bool) -> Parser Text
takeTill :: (Char -> Bool) -> Parser Text
takeTill Char -> Bool
test = (Text -> Result Text) -> Parser Text
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
let n :: Int
n = Int -> Maybe Int -> Int
forall a. a -> Maybe a -> a
fromMaybe (Text -> Int
length Text
inp) (Maybe Int -> Int) -> Maybe Int -> Int
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> Text -> Maybe Int
findIndex Char -> Bool
test Text
inp
(Text
pfx, Text
more) = Int -> Text -> (Text, Text)
splitAt Int
n Text
inp
in Text -> Text -> Result Text
forall a. a -> Text -> Result a
Success Text
pfx Text
more
{-# INLINE CONLIKE takeTill1 #-}
takeTill1 :: (Char -> Bool) -> Parser Text
takeTill1 :: (Char -> Bool) -> Parser Text
takeTill1 Char -> Bool
test = (Char -> Bool) -> Parser Text
Data.Text.Parser.takeTill Char -> Bool
test Parser Text -> (Text -> Bool) -> Parser Text
forall (m :: * -> *) a.
(Alternative m, Monad m) =>
m a -> (a -> Bool) -> m a
`provided` (Bool -> Bool
not (Bool -> Bool) -> (Text -> Bool) -> Text -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Text -> Bool
null)
{-# INLINE CONLIKE match #-}
match :: Parser a -> Parser (Text, a)
match :: forall a. Parser a -> Parser (Text, a)
match Parser a
par = (Text -> Result (Text, a)) -> Parser (Text, a)
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Parser a -> Text -> Result a
forall a. Parser a -> Text -> Result a
runParser Parser a
par Text
inp of
Failure [String]
expected Text
more -> [String] -> Text -> Result (Text, a)
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
Error String
reason Text
more Int
len -> String -> Text -> Int -> Result (Text, a)
forall a. String -> Text -> Int -> Result a
Error String
reason Text
more Int
len
Success a
res Text
more ->
let n :: Int
n = Text -> Int
length Text
more
in (Text, a) -> Text -> Result (Text, a)
forall a. a -> Text -> Result a
Success (Int -> Text -> Text
T.take Int
n Text
inp, a
res) Text
more
{-# INLINE CONLIKE label #-}
label :: String -> Parser a -> Parser a
label :: forall a. String -> Parser a -> Parser a
label String
lbl Parser a
par = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Parser a -> Text -> Result a
forall a. Parser a -> Text -> Result a
runParser Parser a
par Text
inp of
Success a
res Text
more -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Failure [String]
_expected Text
_more -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String
lbl] Text
inp
Error String
reason Text
more Int
len ->
let len' :: Int
len' = Int
len Int -> Int -> Int
forall a. Num a => a -> a -> a
+ (Text -> Int
length Text
inp Int -> Int -> Int
forall a. Num a => a -> a -> a
- Text -> Int
length Text
more)
in String -> Text -> Int -> Result a
forall a. String -> Text -> Int -> Result a
Error String
reason Text
inp Int
len'
{-# INLINE CONLIKE extent #-}
extent :: Parser a -> Parser a
extent :: forall a. Parser a -> Parser a
extent Parser a
par = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case Parser a -> Text -> Result a
forall a. Parser a -> Text -> Result a
runParser Parser a
par Text
inp of
Success a
res Text
more -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Failure [String]
expected Text
more -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String]
expected Text
more
Error String
reason Text
more Int
len ->
let len' :: Int
len' = Int
len Int -> Int -> Int
forall a. Num a => a -> a -> a
+ (Text -> Int
length Text
inp Int -> Int -> Int
forall a. Num a => a -> a -> a
- Text -> Int
length Text
more)
in String -> Text -> Int -> Result a
forall a. String -> Text -> Int -> Result a
Error String
reason Text
inp Int
len'
{-# INLINE takeText #-}
takeText :: Parser Text
takeText :: Parser Text
takeText = (Text -> Result Text) -> Parser Text
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> Text -> Text -> Result Text
forall a. a -> Text -> Result a
Success Text
inp Text
forall a. Monoid a => a
mempty
{-# INLINE endOfInput #-}
endOfInput :: Parser ()
endOfInput :: Parser ()
endOfInput = (Text -> Result ()) -> Parser ()
forall a. (Text -> Result a) -> Parser a
Parser \case
Text
inp | Text -> Bool
null Text
inp -> () -> Text -> Result ()
forall a. a -> Text -> Result a
Success () Text
inp
Text
inp -> [String] -> Text -> Result ()
forall a. [String] -> Text -> Result a
Failure [String
"end of input"] Text
inp
{-# INLINE atEnd #-}
atEnd :: Parser Bool
atEnd :: Parser Bool
atEnd = (Text -> Result Bool) -> Parser Bool
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp -> Bool -> Text -> Result Bool
forall a. a -> Text -> Result a
Success (Text -> Bool
null Text
inp) Text
inp
{-# INLINE signed #-}
signed :: (Num a) => Parser a -> Parser a
signed :: forall a. Num a => Parser a -> Parser a
signed Parser a
runNumber = (Char -> Parser Char
char Char
'-' Parser Char -> Parser a -> Parser a
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (a -> a) -> Parser a -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> a
forall a. Num a => a -> a
negate Parser a
runNumber)
Parser a -> Parser a -> Parser a
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> (Char -> Parser Char
char Char
'+' Parser Char -> Parser a -> Parser a
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Parser a
runNumber)
Parser a -> Parser a -> Parser a
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> (Parser a
runNumber)
{-# INLINE CONLIKE unsafeWithUtf8 #-}
unsafeWithUtf8 :: (BS.ByteString -> Maybe (a, BS.ByteString))
-> Text -> Maybe (a, Text)
unsafeWithUtf8 :: forall a.
(ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
unsafeWithUtf8 ByteString -> Maybe (a, ByteString)
bspar = \Text
inp ->
let bstr :: ByteString
bstr = Text -> ByteString
encodeUtf8 Text
inp
in case ByteString -> Maybe (a, ByteString)
bspar ByteString
bstr of
Maybe (a, ByteString)
Nothing -> Maybe (a, Text)
forall a. Maybe a
Nothing
Just (a
x, ByteString
more) ->
let n :: Int
n = Text -> Int
lengthWord8 Text
inp Int -> Int -> Int
forall a. Num a => a -> a -> a
- ByteString -> Int
BS.length ByteString
more
in (a, Text) -> Maybe (a, Text)
forall a. a -> Maybe a
Just (a
x, Int -> Text -> Text
dropWord8 Int
n Text
inp)
{-# INLINE decimal #-}
decimal :: (Integral a) => Parser a
decimal :: forall a. Integral a => Parser a
decimal = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case (ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
forall a.
(ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
unsafeWithUtf8 ByteString -> Maybe (a, ByteString)
forall a. Integral a => ByteString -> Maybe (a, ByteString)
LI.readDecimal Text
inp of
Just (a
res, Text
more) -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Maybe (a, Text)
Nothing -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String
"decimal"] Text
inp
{-# INLINE hexadecimal #-}
hexadecimal :: (Integral a) => Parser a
hexadecimal :: forall a. Integral a => Parser a
hexadecimal = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case (ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
forall a.
(ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
unsafeWithUtf8 ByteString -> Maybe (a, ByteString)
forall a. Integral a => ByteString -> Maybe (a, ByteString)
LI.readHexadecimal Text
inp of
Just (a
res, Text
more) -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Maybe (a, Text)
Nothing -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String
"hexadecimal"] Text
inp
{-# INLINE octal #-}
octal :: (Integral a) => Parser a
octal :: forall a. Integral a => Parser a
octal = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case (ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
forall a.
(ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
unsafeWithUtf8 ByteString -> Maybe (a, ByteString)
forall a. Integral a => ByteString -> Maybe (a, ByteString)
LI.readOctal Text
inp of
Just (a
res, Text
more) -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Maybe (a, Text)
Nothing -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String
"octal"] Text
inp
{-# INLINE fractional #-}
fractional :: (Fractional a) => Parser a
fractional :: forall a. Fractional a => Parser a
fractional = (Text -> Result a) -> Parser a
forall a. (Text -> Result a) -> Parser a
Parser \Text
inp ->
case (ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
forall a.
(ByteString -> Maybe (a, ByteString)) -> Text -> Maybe (a, Text)
unsafeWithUtf8 ByteString -> Maybe (a, ByteString)
forall a. Fractional a => ByteString -> Maybe (a, ByteString)
LF.readDecimal Text
inp of
Just (a
res, Text
more) -> a -> Text -> Result a
forall a. a -> Text -> Result a
Success a
res Text
more
Maybe (a, Text)
Nothing -> [String] -> Text -> Result a
forall a. [String] -> Text -> Result a
Failure [String
"fractional"] Text
inp