From 70bafc123966d7eb6186c36155088f8c0b5ada25 Mon Sep 17 00:00:00 2001 From: Manu Date: Sun, 12 Oct 2025 15:51:35 +0200 Subject: [PATCH] Ajout des boucles For --- essai.lox | 11 +++++++---- src/interpreter.rs | 5 ++++- src/parser.rs | 44 ++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 55 insertions(+), 5 deletions(-) diff --git a/essai.lox b/essai.lox index 475bef7..bd46d53 100644 --- a/essai.lox +++ b/essai.lox @@ -1,5 +1,8 @@ -var l=3; -while(l>0) { - print l; - l = l-1; +var a = 0; +var temp; + +for (var b = 1; a < 10000; b = temp + b) { + print a; + temp = a; + a = b; } \ No newline at end of file diff --git a/src/interpreter.rs b/src/interpreter.rs index 9d9051a..cb3fcae 100644 --- a/src/interpreter.rs +++ b/src/interpreter.rs @@ -232,7 +232,10 @@ impl StatementVisitor<()> for Interpreter { let value = self.visit_expr(&e).unwrap(); self.environment.define(v.token.literal.clone(), value); } - None => {} + None => { + let value = LiteralNil; + self.environment.define(v.token.literal.clone(), value); + } } } diff --git a/src/parser.rs b/src/parser.rs index e737f09..a4b1ba9 100644 --- a/src/parser.rs +++ b/src/parser.rs @@ -1,3 +1,4 @@ +use std::ptr::null; use crate::expr::{Assign, Binary, Expr, Grouping, Unary, Variable, Logical}; use crate::expr::Expr::LogicalExpr; use crate::expr::Literal::{LiteralBool, LiteralNumber, LiteralString}; @@ -257,6 +258,10 @@ impl Parser { } fn statement(&mut self) -> Result { + if self.match_token(&[TokenType::For]) { + return self.for_statement(); + } + if self.match_token(&[TokenType::If]) { return self.if_statement(); } @@ -288,6 +293,45 @@ impl Parser { Ok(Statement::Block(BlockStatement::new(statements))) } + fn for_statement(&mut self) -> Result { + self.consume(&TokenType::LeftParen, String::from("Expect ("))?; + + let initializer: Statement; + if self.match_token(&[TokenType::Semicolon]) { + initializer = Statement::Block(BlockStatement::new(Vec::new())); + } else if self.match_token(&[TokenType::Var]) { + initializer = self.var_declaration()?; + } else { + initializer = self.expr_statement()?; + } + + let condition: Expr; + if !self.match_token(&[TokenType::Semicolon]) { + condition = self.expression()?; + } else { + condition = Expr::LiteralExpr(LiteralBool(true)); + } + self.consume(&TokenType::Semicolon, String::from("Expect ;"))?; + + let increment: Expr; + if !self.match_token(&[TokenType::RightParen]) { + increment = self.expression()?; + } else { + increment = Expr::LiteralExpr(LiteralBool(true)); + } + self.consume(&TokenType::RightParen, String::from("Expect )"))?; + + let mut for_body: Vec = Vec::new(); + for_body.push(self.statement()?); + for_body.push(Statement::Expression(ExpressionStatement { expr: increment })); + + let mut for_statements: Vec = Vec::new(); + for_statements.push(initializer); + for_statements.push(Statement::While(WhileStatement{ condition, body: Box::new(Statement::Block(BlockStatement::new(for_body)))})); + + Ok(Statement::Block(BlockStatement::new(for_statements))) + } + fn print_statement(&mut self) -> Result { match self.expression() { Ok(e) => {