Compare commits

...

2 commits

Author SHA1 Message Date
Raptorox
a887bf4b3e
don't repeat l/rhs in eval 2026-05-21 17:40:53 +02:00
Raptorox
8c507cb1da
add exponentiation 2026-05-21 17:39:43 +02:00
5 changed files with 17 additions and 8 deletions

View file

@ -20,12 +20,16 @@ impl Evaluator {
} }
}, },
Expr::Binary { op, left, right } => { Expr::Binary { op, left, right } => {
let lhs = self.eval_expr(*left);
let rhs = self.eval_expr(*right);
match op { match op {
BinaryOp::Add => self.eval_expr(*left) + self.eval_expr(*right), BinaryOp::Add => lhs + rhs,
BinaryOp::Sub => self.eval_expr(*left) - self.eval_expr(*right), BinaryOp::Sub => lhs - rhs,
BinaryOp::Mul => self.eval_expr(*left) * self.eval_expr(*right), BinaryOp::Mul => lhs * rhs,
BinaryOp::Div => self.eval_expr(*left) / self.eval_expr(*right), BinaryOp::Div => lhs / rhs,
BinaryOp::Mod => self.eval_expr(*left) % self.eval_expr(*right) BinaryOp::Mod => lhs % rhs,
BinaryOp::Exp => lhs.pow(rhs as u32) // probably shouldn't cast like that
} }
}, },
expr => panic!("can't eval expression: {expr:?}") expr => panic!("can't eval expression: {expr:?}")

View file

@ -4,7 +4,8 @@ pub enum BinaryOp {
Sub, Sub,
Mul, Mul,
Div, Div,
Mod Mod,
Exp
} }
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
@ -14,14 +15,15 @@ pub enum UnaryOp {
pub fn prefix_bp(op: &UnaryOp) -> u8 { pub fn prefix_bp(op: &UnaryOp) -> u8 {
match op { match op {
UnaryOp::Neg => 5 UnaryOp::Neg => 7
} }
} }
pub fn infix_bp(op: &BinaryOp) -> (u8, u8) { pub fn infix_bp(op: &BinaryOp) -> (u8, u8) {
match op { match op {
BinaryOp::Add | BinaryOp::Sub => (1, 2), BinaryOp::Add | BinaryOp::Sub => (1, 2),
BinaryOp::Mul | BinaryOp::Div | BinaryOp::Mod => (3, 4) BinaryOp::Mul | BinaryOp::Div | BinaryOp::Mod => (3, 4),
BinaryOp::Exp => (5, 6)
} }
} }

View file

@ -59,6 +59,7 @@ impl Lexer {
Some(b'*') => {self.advance(); Some(Token::Asterisk)}, Some(b'*') => {self.advance(); Some(Token::Asterisk)},
Some(b'/') => {self.advance(); Some(Token::Slash)}, Some(b'/') => {self.advance(); Some(Token::Slash)},
Some(b'%') => {self.advance(); Some(Token::Percent)}, Some(b'%') => {self.advance(); Some(Token::Percent)},
Some(b'^') => {self.advance(); Some(Token::Caret)},
Some(b'(') => {self.advance(); Some(Token::LParen)}, Some(b'(') => {self.advance(); Some(Token::LParen)},
Some(b')') => {self.advance(); Some(Token::RParen)}, Some(b')') => {self.advance(); Some(Token::RParen)},

View file

@ -69,6 +69,7 @@ impl Parser {
Some(Token::Asterisk) => BinaryOp::Mul, Some(Token::Asterisk) => BinaryOp::Mul,
Some(Token::Slash) => BinaryOp::Div, Some(Token::Slash) => BinaryOp::Div,
Some(Token::Percent) => BinaryOp::Mod, Some(Token::Percent) => BinaryOp::Mod,
Some(Token::Caret) => BinaryOp::Exp,
_ => break _ => break
}; };

View file

@ -9,6 +9,7 @@ pub enum Token {
Asterisk, Asterisk,
Slash, Slash,
Percent, Percent,
Caret,
// Parentheses // Parentheses
LParen, LParen,