CLIPPY IS GOD.

This commit is contained in:
Emmanuel BENOîT 2023-01-02 14:10:32 +01:00
parent 2f0798bfe1
commit a317e54426
3 changed files with 28 additions and 45 deletions

View file

@ -18,7 +18,7 @@ pub enum StmtNode {
/// The print statement /// The print statement
Print(ExprNode), Print(ExprNode),
/// A block containing multiple statements. /// A block containing multiple statements.
Block(Vec<Box<StmtNode>>), Block(Vec<StmtNode>),
/// A conditional statement. /// A conditional statement.
IfStmt { IfStmt {
condition: ExprNode, condition: ExprNode,
@ -100,7 +100,7 @@ impl AstDumper for StmtNode {
match self { match self {
Self::VarDecl(name, Some(expr)) => format!("( var {} {} )", name.lexeme, expr.dump()), Self::VarDecl(name, Some(expr)) => format!("( var {} {} )", name.lexeme, expr.dump()),
Self::VarDecl(name, None) => format!("( var {} nil )", name.lexeme), Self::VarDecl(name, None) => format!("( var {} nil )", name.lexeme),
Self::Expression(expr) => format!("{}", expr.dump()), Self::Expression(expr) => expr.dump(),
Self::Print(expr) => format!("(print {})", expr.dump()), Self::Print(expr) => format!("(print {})", expr.dump()),
Self::Block(stmts) => format!( Self::Block(stmts) => format!(

View file

@ -39,9 +39,9 @@ impl Default for InterpreterFlowControl {
} }
} }
impl Into<InterpreterFlowControl> for Value { impl From<Value> for InterpreterFlowControl {
fn into(self: Self) -> InterpreterFlowControl { fn from(value: Value) -> Self {
InterpreterFlowControl::Result(self) Self::Result(value)
} }
} }
@ -98,7 +98,7 @@ impl Interpretable for ast::StmtNode {
label, label,
condition, condition,
body, body,
after_body after_body,
} => self.on_loop_statement(environment, label, condition, body, after_body), } => self.on_loop_statement(environment, label, condition, body, after_body),
ast::StmtNode::LoopControlStmt { ast::StmtNode::LoopControlStmt {
is_break, is_break,
@ -139,11 +139,7 @@ impl ast::StmtNode {
} }
/// Execute the contents of a block. /// Execute the contents of a block.
fn on_block( fn on_block(&self, environment: &EnvironmentRef, stmts: &[ast::StmtNode]) -> InterpreterResult {
&self,
environment: &EnvironmentRef,
stmts: &Vec<Box<ast::StmtNode>>,
) -> InterpreterResult {
let child = Environment::create_child(environment); let child = Environment::create_child(environment);
for stmt in stmts.iter() { for stmt in stmts.iter() {
let result = stmt.interprete(&child)?; let result = stmt.interprete(&child)?;
@ -180,10 +176,7 @@ impl ast::StmtNode {
body: &ast::StmtNode, body: &ast::StmtNode,
after_body: &Option<Box<ast::StmtNode>>, after_body: &Option<Box<ast::StmtNode>>,
) -> InterpreterResult { ) -> InterpreterResult {
let ln = match label { let ln = label.as_ref().map(|token| token.lexeme.clone());
None => None,
Some(token) => Some(token.lexeme.clone()),
};
while condition.interprete(environment)?.result().is_truthy() { while condition.interprete(environment)?.result().is_truthy() {
let result = body.interprete(environment)?; let result = body.interprete(environment)?;
match &result { match &result {
@ -211,10 +204,7 @@ impl ast::StmtNode {
is_break: bool, is_break: bool,
label: &Option<Token>, label: &Option<Token>,
) -> InterpreterResult { ) -> InterpreterResult {
let name = match label { let name = label.as_ref().map(|token| token.lexeme.clone());
None => None,
Some(token) => Some(token.lexeme.clone()),
};
if is_break { if is_break {
Ok(InterpreterFlowControl::Break(name)) Ok(InterpreterFlowControl::Break(name))
} else { } else {
@ -263,9 +253,9 @@ impl ast::ExprNode {
right: &ast::ExprNode, right: &ast::ExprNode,
) -> InterpreterResult { ) -> InterpreterResult {
let left_value = left.interprete(environment)?.result(); let left_value = left.interprete(environment)?.result();
if operator.token_type == TokenType::Or && left_value.is_truthy() { if operator.token_type == TokenType::Or && left_value.is_truthy()
Ok(left_value.into()) || operator.token_type == TokenType::And && !left_value.is_truthy()
} else if operator.token_type == TokenType::And && !left_value.is_truthy() { {
Ok(left_value.into()) Ok(left_value.into())
} else { } else {
right.interprete(environment) right.interprete(environment)

View file

@ -15,17 +15,17 @@ pub struct Parser {
/// The state of the parser regarding loops. We may be parsing an unnamed or /// The state of the parser regarding loops. We may be parsing an unnamed or
/// named loop, or we might not be parsing a loop at all. /// named loop, or we might not be parsing a loop at all.
#[derive(Debug, Clone, PartialEq)] #[derive(Debug, Clone, PartialEq)]
pub enum LoopParsingState { enum LoopParsingState {
NoLoop, None,
UnnamedLoop, Unnamed,
NamedLoop(String), Named(String),
} }
impl From<&Option<Token>> for LoopParsingState { impl From<&Option<Token>> for LoopParsingState {
fn from(value: &Option<Token>) -> Self { fn from(value: &Option<Token>) -> Self {
match &value { match &value {
None => LoopParsingState::UnnamedLoop, None => LoopParsingState::Unnamed,
Some(name) => LoopParsingState::NamedLoop(name.lexeme.clone()), Some(name) => LoopParsingState::Named(name.lexeme.clone()),
} }
} }
} }
@ -46,7 +46,7 @@ impl Parser {
/// Parse the tokens into an AST and return it, or return nothing if a /// Parse the tokens into an AST and return it, or return nothing if a
/// parser error occurs. /// parser error occurs.
pub fn parse(mut self, err_hdl: &mut ErrorHandler) -> Option<ast::ProgramNode> { pub fn parse(mut self, err_hdl: &mut ErrorHandler) -> Option<ast::ProgramNode> {
self.loop_state.push(LoopParsingState::NoLoop); self.loop_state.push(LoopParsingState::None);
let result = self.parse_program(err_hdl); let result = self.parse_program(err_hdl);
self.loop_state.pop(); self.loop_state.pop();
result result
@ -172,10 +172,9 @@ impl Parser {
/// block := "{" statement* "}" /// block := "{" statement* "}"
/// ``` /// ```
fn parse_block(&mut self) -> ParserResult<ast::StmtNode> { fn parse_block(&mut self) -> ParserResult<ast::StmtNode> {
let mut stmts: Vec<Box<ast::StmtNode>> = Vec::new(); let mut stmts: Vec<ast::StmtNode> = Vec::new();
while !(self.check(&TokenType::RightBrace) || self.is_at_end()) { while !(self.check(&TokenType::RightBrace) || self.is_at_end()) {
let stmt = self.parse_statement()?; stmts.push(self.parse_statement()?);
stmts.push(Box::new(stmt));
} }
self.consume(&TokenType::RightBrace, "expected '}' after block.")?; self.consume(&TokenType::RightBrace, "expected '}' after block.")?;
Ok(ast::StmtNode::Block(stmts)) Ok(ast::StmtNode::Block(stmts))
@ -314,16 +313,10 @@ impl Parser {
label, label,
condition, condition,
body: Box::new(body_stmt), body: Box::new(body_stmt),
after_body: match increment { after_body: increment.map(|incr| Box::new(ast::StmtNode::Expression(incr))),
Some(incr) => Some(Box::new(ast::StmtNode::Expression(incr))),
None => None,
},
}; };
if let Some(init_stmt) = initializer { if let Some(init_stmt) = initializer {
Ok(ast::StmtNode::Block(vec![ Ok(ast::StmtNode::Block(vec![init_stmt, while_stmt]))
Box::new(init_stmt),
Box::new(while_stmt),
]))
} else { } else {
Ok(while_stmt) Ok(while_stmt)
} }
@ -335,7 +328,7 @@ impl Parser {
/// loop_control_statement := "continue" ( IDENTIFIER )? ";" /// loop_control_statement := "continue" ( IDENTIFIER )? ";"
/// ``` /// ```
fn parse_loop_control_statement(&mut self, stmt_token: &Token) -> ParserResult<ast::StmtNode> { fn parse_loop_control_statement(&mut self, stmt_token: &Token) -> ParserResult<ast::StmtNode> {
if self.loop_state() == &LoopParsingState::NoLoop { if self.loop_state() == &LoopParsingState::None {
return Err(ParserError::new( return Err(ParserError::new(
stmt_token, stmt_token,
&format!( &format!(
@ -629,10 +622,10 @@ impl Parser {
let mut pos = self.loop_state.len() - 1; let mut pos = self.loop_state.len() - 1;
loop { loop {
match &self.loop_state[pos] { match &self.loop_state[pos] {
LoopParsingState::NoLoop => break, LoopParsingState::None => break,
LoopParsingState::UnnamedLoop => (), LoopParsingState::Unnamed => (),
LoopParsingState::NamedLoop(n) if n == name => return true, LoopParsingState::Named(n) if n == name => return true,
LoopParsingState::NamedLoop(_) => (), LoopParsingState::Named(_) => (),
} }
pos -= 1; pos -= 1;
} }