Parse loops
This commit is contained in:
parent
5cb86b80df
commit
76be50eab3
@ -4,11 +4,17 @@ use crate::{
|
|||||||
Value,
|
Value,
|
||||||
};
|
};
|
||||||
|
|
||||||
use super::{AbstractTree, Block, Type};
|
use super::{AbstractTree, Statement, Type};
|
||||||
|
|
||||||
#[derive(Clone, Debug, Eq, PartialEq, PartialOrd, Ord)]
|
#[derive(Clone, Debug, Eq, PartialEq, PartialOrd, Ord)]
|
||||||
pub struct Loop<'src> {
|
pub struct Loop<'src> {
|
||||||
block: Block<'src>,
|
statements: Vec<Statement<'src>>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'src> Loop<'src> {
|
||||||
|
pub fn new(statements: Vec<Statement<'src>>) -> Self {
|
||||||
|
Self { statements }
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'src> AbstractTree for Loop<'src> {
|
impl<'src> AbstractTree for Loop<'src> {
|
||||||
|
@ -123,6 +123,7 @@ pub fn lexer<'src>() -> impl Parser<
|
|||||||
just("map").padded(),
|
just("map").padded(),
|
||||||
just("range").padded(),
|
just("range").padded(),
|
||||||
just("str").padded(),
|
just("str").padded(),
|
||||||
|
just("loop").padded(),
|
||||||
))
|
))
|
||||||
.map(Token::Keyword);
|
.map(Token::Keyword);
|
||||||
|
|
||||||
|
@ -7,6 +7,15 @@ use crate::{abstract_tree::*, error::Error, lexer::Token};
|
|||||||
type ParserInput<'tokens, 'src> =
|
type ParserInput<'tokens, 'src> =
|
||||||
SpannedInput<Token<'src>, SimpleSpan, &'tokens [(Token<'src>, SimpleSpan)]>;
|
SpannedInput<Token<'src>, SimpleSpan, &'tokens [(Token<'src>, SimpleSpan)]>;
|
||||||
|
|
||||||
|
pub fn parse<'tokens, 'src: 'tokens>(
|
||||||
|
tokens: &'tokens [(Token<'src>, SimpleSpan)],
|
||||||
|
) -> Result<Vec<(Statement<'src>, SimpleSpan)>, Error<'tokens>> {
|
||||||
|
parser()
|
||||||
|
.parse(tokens.spanned((0..0).into()))
|
||||||
|
.into_result()
|
||||||
|
.map_err(|error| Error::Parse(error))
|
||||||
|
}
|
||||||
|
|
||||||
fn parser<'tokens, 'src: 'tokens>() -> impl Parser<
|
fn parser<'tokens, 'src: 'tokens>() -> impl Parser<
|
||||||
'tokens,
|
'tokens,
|
||||||
ParserInput<'tokens, 'src>,
|
ParserInput<'tokens, 'src>,
|
||||||
@ -158,7 +167,18 @@ fn parser<'tokens, 'src: 'tokens>() -> impl Parser<
|
|||||||
.map(|statements| Statement::Block(Block::new(statements)))
|
.map(|statements| Statement::Block(Block::new(statements)))
|
||||||
.boxed();
|
.boxed();
|
||||||
|
|
||||||
choice((assignment, expression_statement, block))
|
let r#loop = statement
|
||||||
|
.clone()
|
||||||
|
.separated_by(just(Token::Control(";")).or_not())
|
||||||
|
.collect()
|
||||||
|
.delimited_by(
|
||||||
|
just(Token::Keyword("loop")).then(just(Token::Control("{"))),
|
||||||
|
just(Token::Control("}")),
|
||||||
|
)
|
||||||
|
.map(|statements| Statement::Loop(Loop::new(statements)))
|
||||||
|
.boxed();
|
||||||
|
|
||||||
|
choice((assignment, expression_statement, block, r#loop))
|
||||||
});
|
});
|
||||||
|
|
||||||
statement
|
statement
|
||||||
@ -167,21 +187,20 @@ fn parser<'tokens, 'src: 'tokens>() -> impl Parser<
|
|||||||
.collect()
|
.collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn parse<'tokens, 'src: 'tokens>(
|
|
||||||
tokens: &'tokens [(Token<'src>, SimpleSpan)],
|
|
||||||
) -> Result<Vec<(Statement<'src>, SimpleSpan)>, Error<'tokens>> {
|
|
||||||
parser()
|
|
||||||
.parse(tokens.spanned((0..0).into()))
|
|
||||||
.into_result()
|
|
||||||
.map_err(|error| Error::Parse(error))
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use crate::{abstract_tree::Logic, lexer::lex};
|
use crate::{abstract_tree::Logic, lexer::lex};
|
||||||
|
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn r#loop() {
|
||||||
|
assert_eq!(
|
||||||
|
parse(&lex("loop {}").unwrap()).unwrap()[0].0,
|
||||||
|
Statement::Loop(Loop::new(vec![]))
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn block() {
|
fn block() {
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
|
Loading…
Reference in New Issue
Block a user