module GLL.Combinators.Lexer (
    default_lexer, lexer, lexerEither, LexerSettings(..), emptyLanguage,
    oneOf, manyOf, someOf, baseToDec,
    ) where

import GLL.Types.Grammar (Token(..), SubsumesToken(..))
import Data.List (isPrefixOf)
import Data.Char (isSpace, isDigit, isAlpha, isUpper, isLower)
import Text.Regex.Applicative
import Text.Regex.Applicative.Common (signed)

-- | Settings for changing the behaviour of the builtin lexer 'lexer'.
-- Lexers are built using "Text.Regex.Applicative".
data LexerSettings = LexerSettings {
        -- | Which keychars to recognise? Default: none.
        LexerSettings -> [Char]
keychars        :: [Char]
        -- | Which keywords to recognise? Default: none.
    ,   LexerSettings -> [[Char]]
keywords        :: [String]
        -- | What is considered a whitespace character? Default: 'Data.Char.isSpace'.
    ,   LexerSettings -> Char -> Bool
whitespace      :: Char -> Bool
        -- | How does a line comment start? Default: '"'//'"'.
    ,   LexerSettings -> [Char]
lineComment     :: String
        -- | How does a block comment open? Default: '"'{-'"'. 
    ,   LexerSettings -> [Char]
blockCommentOpen :: String
        -- | How does a block comment close? Default: '"'-}'"'.
    ,   LexerSettings -> [Char]
blockCommentClose :: String
        -- | How to recognise identifiers? Default alphanumerical with lowercase alpha start.
    ,   LexerSettings -> RE Char [Char]
identifiers     :: RE Char String
        -- | How to recognise alternative identifiers? Default alphanumerical with uppercase alpha start.
    ,   LexerSettings -> RE Char [Char]
altIdentifiers  :: RE Char String
        -- | Arbitrary tokens /(a,b)/. /a/ is the token name, /b/ is a regular expression.
    ,   LexerSettings -> [([Char], RE Char [Char])]
tokens          :: [(String, RE Char String)]
        -- | Whether integer literals may be signed positive or negative. Default: 'False'
    ,   LexerSettings -> Bool
signed_int_lits :: Bool
    }

-- | The default 'LexerSettings'.
emptyLanguage :: LexerSettings
emptyLanguage :: LexerSettings
emptyLanguage = [Char]
-> [[Char]]
-> (Char -> Bool)
-> [Char]
-> [Char]
-> [Char]
-> RE Char [Char]
-> RE Char [Char]
-> [([Char], RE Char [Char])]
-> Bool
-> LexerSettings
LexerSettings [] [] Char -> Bool
isSpace [Char]
"//" [Char]
"{-" [Char]
"-}"
    ((:) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall s. (s -> Bool) -> RE s s
psym Char -> Bool
isLower forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char [Char]
lowercase_id)
    ((:) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall s. (s -> Bool) -> RE s s
psym Char -> Bool
isUpper forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char [Char]
lowercase_id)
    [] Bool
False
 where lowercase_id :: RE Char [Char]
lowercase_id = forall (f :: * -> *) a. Alternative f => f a -> f [a]
many (forall s. (s -> Bool) -> RE s s
psym (\Char
c -> Char -> Bool
isAlpha Char
c Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'_' Bool -> Bool -> Bool
|| Char -> Bool
isDigit Char
c))

-- | A lexer using the default 'LexerSettings'.
default_lexer :: SubsumesToken t => String -> [t]
default_lexer :: forall t. SubsumesToken t => [Char] -> [t]
default_lexer = forall t. SubsumesToken t => LexerSettings -> [Char] -> [t]
lexer LexerSettings
emptyLanguage 

-- | Variant of 'lexerEither' that throws an error or returns the result otherwise
lexer :: SubsumesToken t => LexerSettings -> String -> [t]
lexer :: forall t. SubsumesToken t => LexerSettings -> [Char] -> [t]
lexer LexerSettings
set [Char]
inp = case forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
set [Char]
inp of
  Left [Char]
err  -> forall a. HasCallStack => [Char] -> a
error [Char]
err
  Right [t]
ts  -> [t]
ts

-- | A lexer parameterised by 'LexerSettings'.
lexerEither :: SubsumesToken t => LexerSettings -> String -> Either String [t]
lexerEither :: forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
_ [] = forall a b. b -> Either a b
Right []
lexerEither LexerSettings
lexsets [Char]
s
  | [Char]
start forall a. Eq a => a -> a -> Bool
/= [Char]
"" Bool -> Bool -> Bool
&& [Char]
end forall a. Eq a => a -> a -> Bool
/= [Char]
"" Bool -> Bool -> Bool
&& [Char]
start forall a. Eq a => [a] -> [a] -> Bool
`isPrefixOf` [Char]
s = forall t. SubsumesToken t => Int -> [Char] -> Either [Char] [t]
blockState Int
1 (forall a. Int -> [a] -> [a]
drop Int
lS [Char]
s)
  | [Char]
lComm forall a. Eq a => a -> a -> Bool
/= [Char]
"" Bool -> Bool -> Bool
&& [Char]
lComm forall a. Eq a => [a] -> [a] -> Bool
`isPrefixOf` [Char]
s = case forall a. (a -> Bool) -> [a] -> [a]
dropWhile (forall a. Eq a => a -> a -> Bool
(/=) Char
'\n') [Char]
s of
      []      -> forall a b. b -> Either a b
Right []
      (Char
c:[Char]
cs)  -> forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
lexsets [Char]
cs
  | Char -> Bool
isWS (forall a. [a] -> a
head [Char]
s) = forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
lexsets (forall a. (a -> Bool) -> [a] -> [a]
dropWhile Char -> Bool
isWS [Char]
s)
  | Bool
otherwise = case forall s a. RE s a -> [s] -> Maybe (a, [s])
findLongestPrefix (forall t. SubsumesToken t => LexerSettings -> RE Char t
lTokens LexerSettings
lexsets) [Char]
s of
        Just (t
tok, [Char]
rest)   -> forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (t
tok forall a. a -> [a] -> [a]
:) forall a b. (a -> b) -> a -> b
$ forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
lexsets [Char]
rest
        Maybe (t, [Char])
Nothing            -> forall a b. a -> Either a b
Left ([Char]
"lexical error at: " forall a. [a] -> [a] -> [a]
++ forall a. Show a => a -> [Char]
show (forall a. Int -> [a] -> [a]
take Int
10 [Char]
s))
  where start :: [Char]
start = LexerSettings -> [Char]
blockCommentOpen LexerSettings
lexsets
        end :: [Char]
end   = LexerSettings -> [Char]
blockCommentClose LexerSettings
lexsets
        isWS :: Char -> Bool
isWS  = LexerSettings -> Char -> Bool
whitespace LexerSettings
lexsets
        lComm :: [Char]
lComm = LexerSettings -> [Char]
lineComment LexerSettings
lexsets
        lS :: Int
lS    = forall (t :: * -> *) a. Foldable t => t a -> Int
length [Char]
start
        lE :: Int
lE    = forall (t :: * -> *) a. Foldable t => t a -> Int
length [Char]
end

        blockState :: SubsumesToken t => Int -> String -> Either String [t] 
        blockState :: forall t. SubsumesToken t => Int -> [Char] -> Either [Char] [t]
blockState Int
n [] = forall a b. b -> Either a b
Right [] 
        blockState Int
0 [Char]
rest = forall t.
SubsumesToken t =>
LexerSettings -> [Char] -> Either [Char] [t]
lexerEither LexerSettings
lexsets [Char]
rest
        blockState Int
n [Char]
cs | [Char]
start forall a. Eq a => [a] -> [a] -> Bool
`isPrefixOf` [Char]
cs = forall t. SubsumesToken t => Int -> [Char] -> Either [Char] [t]
blockState (Int
nforall a. Num a => a -> a -> a
+Int
1) (forall a. Int -> [a] -> [a]
drop Int
lS [Char]
cs)
                    | [Char]
end forall a. Eq a => [a] -> [a] -> Bool
`isPrefixOf` [Char]
cs   = forall t. SubsumesToken t => Int -> [Char] -> Either [Char] [t]
blockState (Int
nforall a. Num a => a -> a -> a
-Int
1) (forall a. Int -> [a] -> [a]
drop Int
lE [Char]
cs) 
                    | Bool
otherwise             = forall t. SubsumesToken t => Int -> [Char] -> Either [Char] [t]
blockState Int
n (forall a. [a] -> [a]
tail [Char]
cs)

lTokens :: SubsumesToken t => LexerSettings -> RE Char t 
lTokens :: forall t. SubsumesToken t => LexerSettings -> RE Char t
lTokens LexerSettings
lexsets =
        RE Char t
lCharacters
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> RE Char t
lKeywords
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe Int -> Token
IntLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Bool -> RE Char Int
lIntegers (LexerSettings -> Bool
signed_int_lits LexerSettings
lexsets) 
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe Double -> Token
FloatLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char Double
lFloats
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe [Char] -> Token
IDLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> LexerSettings -> RE Char [Char]
identifiers LexerSettings
lexsets 
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe [Char] -> Token
AltIDLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> LexerSettings -> RE Char [Char]
altIdentifiers LexerSettings
lexsets
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe Char -> Token
CharLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char Char
lCharLit
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. Maybe [Char] -> Token
StringLit forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char [Char]
lStringLit
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> RE Char t
lMore
  where     lMore :: RE Char t
lMore = forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
(<|>) forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b c. (a -> b -> c) -> (a, b) -> c
uncurry forall {f :: * -> *} {b}.
(Functor f, SubsumesToken b) =>
[Char] -> f [Char] -> f b
lToken) forall (f :: * -> *) a. Alternative f => f a
empty (LexerSettings -> [([Char], RE Char [Char])]
tokens LexerSettings
lexsets)

            lChar :: Char -> RE Char a
lChar Char
c = forall a. SubsumesToken a => Token -> a
upcast (Char -> Token
Char Char
c) forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall s. Eq s => s -> RE s s
sym Char
c
            lCharacters :: RE Char t
lCharacters = forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
(<|>) forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall {a}. SubsumesToken a => Char -> RE Char a
lChar) forall (f :: * -> *) a. Alternative f => f a
empty (LexerSettings -> [Char]
keychars LexerSettings
lexsets)

            lKeyword :: [Char] -> RE Char a
lKeyword [Char]
k  = forall a. SubsumesToken a => Token -> a
upcast ([Char] -> Token
Keyword [Char]
k) forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall a. Eq a => [a] -> RE a [a]
string [Char]
k
            lKeywords :: RE Char t
lKeywords = forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
(<|>) forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall {a}. SubsumesToken a => [Char] -> RE Char a
lKeyword) forall (f :: * -> *) a. Alternative f => f a
empty (LexerSettings -> [[Char]]
keywords LexerSettings
lexsets)

lToken :: [Char] -> f [Char] -> f b
lToken [Char]
t f [Char]
re = forall a. SubsumesToken a => Token -> a
upcast forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Char] -> Maybe [Char] -> Token
Token [Char]
t forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> f [Char]
re

lStringLit :: RE Char [Char]
lStringLit = forall {a}. Read a => [Char] -> a
toString forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall s. Eq s => s -> RE s s
sym Char
'\"' forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall (f :: * -> *) a. Alternative f => f a -> f [a]
many RE Char Char
strChar forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* forall s. Eq s => s -> RE s s
sym Char
'\"'
 where strChar :: RE Char Char
strChar =  forall s. Eq s => s -> RE s s
sym Char
'\\' forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> forall s. Eq s => s -> RE s s
sym Char
'\"'
                  forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall s. (s -> Bool) -> RE s s
psym (forall a. Eq a => a -> a -> Bool
(/=) Char
'\"')
       toString :: [Char] -> a
toString [Char]
inner = forall {a}. Read a => [Char] -> a
read ([Char]
"\"" forall a. [a] -> [a] -> [a]
++ [Char]
inner forall a. [a] -> [a] -> [a]
++ [Char]
"\"")

lCharLit :: RE Char Char
lCharLit = forall a. a -> a
id forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall s. Eq s => s -> RE s s
sym Char
'\'' forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char Char
charChar forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* forall s. Eq s => s -> RE s s
sym Char
'\''
  where charChar :: RE Char Char
charChar = forall s. Eq s => s -> RE s s
sym Char
'\\' forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> forall s. Eq s => s -> RE s s
sym Char
'\''
                    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall s. (s -> Bool) -> RE s s
psym (forall a. Eq a => a -> a -> Bool
(/=) Char
'\'')

lFloats :: RE Char Double
lFloats :: RE Char Double
lFloats = forall a. Num a => RE Char a -> RE Char a
signed ( forall {a}. Read a => [Char] -> a
read forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (
        forall {p}. [Char] -> p -> [Char] -> Maybe [Char] -> [Char]
mkDP forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char [Char]
decimal forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall s. Eq s => s -> RE s s
sym Char
'.' forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char [Char]
decimal forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall (f :: * -> *) a. Alternative f => f a -> f (Maybe a)
optional RE Char [Char]
exponent 
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. [a] -> [a] -> [a]
mkEP forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char [Char]
decimal forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char [Char]
exponent
  ))
  where mkDP :: [Char] -> p -> [Char] -> Maybe [Char] -> [Char]
mkDP [Char]
pre p
_ [Char]
post Maybe [Char]
mexp = [Char]
pre forall a. [a] -> [a] -> [a]
++ [Char]
"." forall a. [a] -> [a] -> [a]
++ [Char]
post forall a. [a] -> [a] -> [a]
++ forall b a. b -> (a -> b) -> Maybe a -> b
maybe [Char]
"" forall a. a -> a
id Maybe [Char]
mexp
        mkEP :: [a] -> [a] -> [a]
mkEP [a]
pre [a]
exp = [a]
pre forall a. [a] -> [a] -> [a]
++ [a]
exp

        exponent :: RE Char [Char]
exponent = Char -> Maybe Char -> [Char] -> [Char]
mk forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (forall s. Eq s => s -> RE s s
sym Char
'e' forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall s. Eq s => s -> RE s s
sym Char
'E') 
                      forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall (f :: * -> *) a. Alternative f => f a -> f (Maybe a)
optional (forall s. Eq s => s -> RE s s
sym Char
'+' forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall s. Eq s => s -> RE s s
sym Char
'-')
                      forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> RE Char [Char]
decimal
         where mk :: Char -> Maybe Char -> [Char] -> [Char]
mk Char
pre Maybe Char
sign [Char]
dec = Char
pre forall a. a -> [a] -> [a]
: forall b a. b -> (a -> b) -> Maybe a -> b
maybe [Char]
"" (forall a. a -> [a] -> [a]
:[]) Maybe Char
sign forall a. [a] -> [a] -> [a]
++ [Char]
dec

lIntegers :: Bool -> RE Char Int
lIntegers :: Bool -> RE Char Int
lIntegers Bool
True = forall a. Num a => RE Char a -> RE Char a
signed RE Char Int
lNaturals
lIntegers Bool
False = RE Char Int
lNaturals

lNaturals :: RE Char Int 
lNaturals :: RE Char Int
lNaturals = 
      (forall {a}. Read a => [Char] -> a
read forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> RE Char [Char]
decimal)
  forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> (Int -> [Char] -> Int
baseToDec Int
16 forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ RE Char [Char]
hexPrefix forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall a. Eq a => [a] -> RE a [a]
someOf ([Char
'0'..Char
'9']forall a. [a] -> [a] -> [a]
++[Char
'A'..Char
'F']forall a. [a] -> [a] -> [a]
++[Char
'a'..Char
'f']))
  forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> (Int -> [Char] -> Int
baseToDec Int
8  forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ RE Char [Char]
octPrefix forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall a. Eq a => [a] -> RE a [a]
someOf [Char
'0'..Char
'7'])
  forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> (Int -> [Char] -> Int
baseToDec Int
2  forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ RE Char [Char]
binPrefix forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall a. Eq a => [a] -> RE a [a]
someOf [Char
'0',Char
'1'])
  where hexPrefix :: RE Char [Char]
hexPrefix = forall a. Eq a => [a] -> RE a [a]
string [Char]
"0x" forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. Eq a => [a] -> RE a [a]
string [Char]
"0X"
        octPrefix :: RE Char [Char]
octPrefix = forall a. Eq a => [a] -> RE a [a]
string [Char]
"0o" forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. Eq a => [a] -> RE a [a]
string [Char]
"0O"
        binPrefix :: RE Char [Char]
binPrefix = forall a. Eq a => [a] -> RE a [a]
string [Char]
"0b" forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> forall a. Eq a => [a] -> RE a [a]
string [Char]
"0B" 
    
decimal :: RE Char String
decimal :: RE Char [Char]
decimal = forall a. Eq a => [a] -> RE a [a]
someOf [Char
'0'..Char
'9'] 
 
-- | Convert numerical representation in a given base 
--  (max base = 16, written as string)
--  into decimal representation (returned as Int)
baseToDec :: Int -> String -> Int
baseToDec :: Int -> [Char] -> Int
baseToDec Int
base = forall {t}. Num t => t -> t -> [t] -> t
baseToDec' Int
0 Int
base forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map forall {a}. (Num a, Read a) => Char -> a
toInt
  where baseToDec' :: t -> t -> [t] -> t
baseToDec' t
acc t
base [] = t
acc
        baseToDec' t
acc t
base (t
d:[t]
ds) = t -> t -> [t] -> t
baseToDec' (t
acc forall a. Num a => a -> a -> a
* t
base forall a. Num a => a -> a -> a
+ t
d) t
base [t]
ds
        toInt :: Char -> a
toInt Char
c | Char
c forall a. Eq a => a -> a -> Bool
== Char
'A' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'a' = a
10
                | Char
c forall a. Eq a => a -> a -> Bool
== Char
'B' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'b' = a
11
                | Char
c forall a. Eq a => a -> a -> Bool
== Char
'C' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'c' = a
12
                | Char
c forall a. Eq a => a -> a -> Bool
== Char
'D' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'd' = a
13
                | Char
c forall a. Eq a => a -> a -> Bool
== Char
'E' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'e' = a
14
                | Char
c forall a. Eq a => a -> a -> Bool
== Char
'F' Bool -> Bool -> Bool
|| Char
c forall a. Eq a => a -> a -> Bool
== Char
'f' = a
15
                | Bool
otherwise = forall {a}. Read a => [Char] -> a
read [Char
c]
 
oneOf :: Eq t => [t] -> RE t t       
oneOf :: forall t. Eq t => [t] -> RE t t
oneOf [t]
ts = forall s. (s -> Bool) -> RE s s
psym (\t
t -> t
t forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [t]
ts)

manyOf :: Eq t => [t] -> RE t [t]
manyOf :: forall a. Eq a => [a] -> RE a [a]
manyOf [t]
ts = forall (f :: * -> *) a. Alternative f => f a -> f [a]
many (forall t. Eq t => [t] -> RE t t
oneOf [t]
ts) 

someOf :: Eq t => [t] -> RE t [t]
someOf :: forall a. Eq a => [a] -> RE a [a]
someOf [t]
ts = forall (f :: * -> *) a. Alternative f => f a -> f [a]
some (forall t. Eq t => [t] -> RE t t
oneOf [t]
ts) 

{-

manyOf :: Eq t => [t] -> RE t [t]
manyOf ts = empty <|> someOf ts

someOf :: Eq t => [t] -> RE t [t]
someOf ts = (:) <$> oneOf ts <*> manyOf ts

-}