From 4bc2dab659b7fea42694809872d9c6efaf1446c1 Mon Sep 17 00:00:00 2001 From: Ivan Gromov Date: Sat, 23 Sep 2023 23:05:54 +0100 Subject: [PATCH] Impl Display for Expr, fix tests --- src/ast/expr.rs | 21 +++++++++++++++++++++ src/ast/parser.rs | 28 ++++++++++++++++++++++------ src/ast/token_iterator.rs | 9 +++++++-- src/interpreter.rs | 4 ++-- src/scanner/mod.rs | 3 ++- src/scanner/scanner_iterator.rs | 2 +- 6 files changed, 55 insertions(+), 12 deletions(-) diff --git a/src/ast/expr.rs b/src/ast/expr.rs index bbafd5b..874a4c4 100644 --- a/src/ast/expr.rs +++ b/src/ast/expr.rs @@ -88,6 +88,21 @@ pub enum ExprType { Variable { name: String }, } +impl Display for ExprType { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + ExprType::StringLiteral(s) => write!(f, "\"{}\"", s), + ExprType::NumberLiteral(n) => write!(f, "{}", n), + ExprType::BooleanLiteral(b) => write!(f, "{}", b), + ExprType::Nil => write!(f, "Nil"), + ExprType::Unary(op, right) => write!(f, "{}{}", op, right), + ExprType::Binary(left, op, right) => write!(f, "{}{}{}", left, op, right), + ExprType::Grouping(expr) => write!(f, "({})", expr), + ExprType::Variable { name } => write!(f, "{}", name), + } + } +} + #[derive(PartialEq, Debug, Clone)] pub struct Expr { pub expr_type: ExprType, @@ -127,3 +142,9 @@ impl Expr { Box::new(self.clone()) } } + +impl Display for Expr { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + write!(f, "{}", self.expr_type) + } +} diff --git a/src/ast/parser.rs b/src/ast/parser.rs index e2b4d0c..cc896a4 100644 --- a/src/ast/parser.rs +++ b/src/ast/parser.rs @@ -203,11 +203,26 @@ impl Parser<'_> { message: "Expected expression.".to_owned(), }), Some(t) => match &t.type_ { - TokenType::Nil => Ok(Expr::nil(t.position.clone())), - TokenType::False => Ok(Expr::boolean_literal(false, t.position.clone())), - TokenType::True => Ok(Expr::boolean_literal(true, t.position.clone())), - TokenType::Number(n) => Ok(Expr::number_literal(*n, t.position.clone())), - TokenType::String(s) => Ok(Expr::string_literal(s, t.position.clone())), + TokenType::Nil => { + self.token_iterator.next(); + Ok(Expr::nil(t.position.clone())) + }, + TokenType::False => { + self.token_iterator.next(); + Ok(Expr::boolean_literal(false, t.position.clone())) + }, + TokenType::True => { + self.token_iterator.next(); + Ok(Expr::boolean_literal(true, t.position.clone())) + }, + TokenType::Number(n) => { + self.token_iterator.next(); + Ok(Expr::number_literal(*n, t.position.clone())) + }, + TokenType::String(s) => { + self.token_iterator.next(); + Ok(Expr::string_literal(s, t.position.clone())) + }, TokenType::Identifier(name) => { let position = t.position.clone(); self.token_iterator.next(); @@ -251,7 +266,8 @@ impl Parser<'_> { } fn consume_if_matches(&mut self, token_types: &[TokenType]) -> Option { - match self.token_iterator.peek() { + let peek = self.token_iterator.peek(); + match peek { None => None, Some(t) if (*token_types) diff --git a/src/ast/token_iterator.rs b/src/ast/token_iterator.rs index 0c79eed..c91342f 100644 --- a/src/ast/token_iterator.rs +++ b/src/ast/token_iterator.rs @@ -1,6 +1,6 @@ use std::iter::Peekable; -use crate::{token::Token, position::PositionRange}; +use crate::{token::Token, position::{PositionRange, Position}}; pub struct TokenIterator<'a> { token_iterator: Peekable>, @@ -11,7 +11,12 @@ impl<'a> TokenIterator<'a> { pub fn new(tokens: &'a Vec) -> Self { Self { token_iterator: tokens.iter().peekable(), - last_position: None, + last_position: Some(PositionRange { start: Position { + line: 0, + column: 0, + }, end: Position { + line: 0, column: 0, + } }), } } diff --git a/src/interpreter.rs b/src/interpreter.rs index 6628538..1a686b8 100644 --- a/src/interpreter.rs +++ b/src/interpreter.rs @@ -305,11 +305,11 @@ mod run_tests { kind: LoxErrorKind::Runtime, position: PositionRange { start: Position { line: 0, - column: 0, + column: 1, }, end: Position { line: 0, - column: 0, + column: 11, } }, message: "Unsupported operand types for binary operator + (String(abc), Number(123))".to_owned(), diff --git a/src/scanner/mod.rs b/src/scanner/mod.rs index 0c0ae54..cd4e7e9 100644 --- a/src/scanner/mod.rs +++ b/src/scanner/mod.rs @@ -1,3 +1,4 @@ + mod scanner_iterator; use std::{vec::Vec}; @@ -259,7 +260,7 @@ pub fn scan(source: &str) -> Result, LoxError> { let current_position = it.current_position(); Position { line: current_position.line, - column: current_position.column - token_type.size() + 1, + column: current_position.column + 1 - token_type.size(), } }), end: it.current_position(), diff --git a/src/scanner/scanner_iterator.rs b/src/scanner/scanner_iterator.rs index 8a9e299..f34c6a3 100644 --- a/src/scanner/scanner_iterator.rs +++ b/src/scanner/scanner_iterator.rs @@ -44,7 +44,7 @@ impl<'a> Iterator for ScannerIterator<'a> { } match next { Some(c) if c == '\n' => self.prev_char_is_line_break = true, - _ => {}, + _ => self.prev_char_is_line_break = false, } next }