feat: Add support for if and compound statements.

This commit is contained in:
Jooris Hadeler
2026-01-15 21:38:07 +01:00
parent 10fd3b6abf
commit 6f19d38bf0
4 changed files with 50 additions and 1 deletions

View File

@@ -67,5 +67,15 @@ pub enum Statement {
value: Option<Expression>, value: Option<Expression>,
}, },
If {
condition: Expression,
then: Box<Statement>,
elze: Option<Box<Statement>>,
},
Compound {
body: Vec<Statement>,
},
Expr(Expression), Expr(Expression),
} }

View File

@@ -5,7 +5,7 @@ pub mod parser;
pub mod token; pub mod token;
fn main() { fn main() {
let mut parser = Parser::new("let index = 12 + 3;"); let mut parser = Parser::new("if a < 12 { let b = 10; } else { let c = 20; }");
println!("{:#?}", parser.parse_statement()); println!("{:#?}", parser.parse_statement());
} }

View File

@@ -59,6 +59,7 @@ impl<'src> Parser<'src> {
pub fn parse_statement(&mut self) -> ParserResult<Statement> { pub fn parse_statement(&mut self) -> ParserResult<Statement> {
match self.peek_no_eof()?.kind { match self.peek_no_eof()?.kind {
TokenKind::KwLet => self.parse_let_statement(), TokenKind::KwLet => self.parse_let_statement(),
TokenKind::KwIf => self.parse_if_statement(),
_ => { _ => {
let expr = self.parse_expression(0)?; let expr = self.parse_expression(0)?;
@@ -68,6 +69,42 @@ impl<'src> Parser<'src> {
} }
} }
fn parse_if_statement(&mut self) -> ParserResult<Statement> {
self.expect(&[TokenKind::KwIf])?;
let condition = self.parse_expression(0)?;
let then = Box::new(self.parse_compound_statement()?);
let elze = if self.is_peek(TokenKind::KwElse) {
self.consume();
Some(Box::new(if self.is_peek(TokenKind::KwIf) {
self.parse_if_statement()?
} else {
self.parse_compound_statement()?
}))
} else {
None
};
Ok(Statement::If {
condition,
then,
elze,
})
}
fn parse_compound_statement(&mut self) -> ParserResult<Statement> {
let mut body = Vec::new();
self.expect(&[TokenKind::LeftBrace])?;
while !self.is_peek(TokenKind::RightBrace) {
body.push(self.parse_statement()?);
}
self.expect(&[TokenKind::RightBrace])?;
Ok(Statement::Compound { body })
}
fn parse_let_statement(&mut self) -> ParserResult<Statement> { fn parse_let_statement(&mut self) -> ParserResult<Statement> {
self.expect(&[TokenKind::KwLet])?; self.expect(&[TokenKind::KwLet])?;

View File

@@ -42,6 +42,7 @@ pub enum TokenKind {
KwFn, KwFn,
KwIf, KwIf,
KwLet, KwLet,
KwElse,
KwLoop, KwLoop,
KwWhile, KwWhile,
KwBreak, KwBreak,
@@ -183,6 +184,7 @@ impl<'src> Tokenizer<'src> {
"fn" => TokenKind::KwFn, "fn" => TokenKind::KwFn,
"if" => TokenKind::KwIf, "if" => TokenKind::KwIf,
"let" => TokenKind::KwLet, "let" => TokenKind::KwLet,
"else" => TokenKind::KwElse,
"loop" => TokenKind::KwLoop, "loop" => TokenKind::KwLoop,
"while" => TokenKind::KwWhile, "while" => TokenKind::KwWhile,
"break" => TokenKind::KwBreak, "break" => TokenKind::KwBreak,