L0
(( Under construction! ))
Parsing Expresssions
Recall that we use the same type for L0 expressions as we do for MicroLaTeX and XMarkdown:
-- Parser.Expr
type Expr
= Fun String (List Expr) Meta
| Text String Meta
| Verbatim String String Meta
The parser for expressions uses the shift-reduce strategy and is implemented as a functional loop with state where the state is given by
-- L0.Parser.Expression
type alias State =
{ step : Int
, tokens : List Token
, numberOfTokens : Int
, tokenIndex : Int
, committed : List Expr
, stack : List Token
, messages : List String
, lineNumber : Int
}
with driving function State -> Step State State
defined by
-- L0.Parser.Expression
nextStep : State -> Step State State
nextStep state =
case getToken state of
Nothing ->
if stackIsEmpty state then
Done state
else
recoverFromError state
Just token ->
state
|> advanceTokenIndex
|> pushOrCommit token
|> reduceState
|> (\st -> { st | step = st.step + 1 })
|> Loop
The reduceState
function asks whether the stack
is reducible using the function isReducible
discussed
below. If it is, it reduces the stack using
reduceStack
, returning the updated state. If not,
the state is passed on unchanged.
-- L0.Parser.Expression
reduceState : State -> State
reduceState state =
if tokensAreReducible state then
{ state | stack = [], committed = reduceStack state ++ state.committed }
else
state
Reducibility
-- L0.Parser.Match:
isReducible : List Symbol -> Bool
isReducible symbols_ =
let
symbols =
List.filter (\sym -> sym /= WS) symbols_
in
case symbols of
M :: rest ->
List.head (List.reverse rest) == Just M
C :: rest ->
List.head (List.reverse rest) == Just C
L :: ST :: rest ->
case List.head (List.reverse rest) of
Just R ->
hasReducibleArgs (dropLast rest)
_ ->
False
_ ->
False