From 6b24456f87c2345946eaf3ee1bdfdc9bd4f31529 Mon Sep 17 00:00:00 2001 From: Austen Adler Date: Sat, 2 Oct 2021 08:44:45 -0400 Subject: [PATCH] Use lazy_static for mapping operations --- Cargo.lock | 3 + Cargo.toml | 1 + src/calc.rs | 161 ++++++++++++++++++++--------------------- src/calc/operations.rs | 6 +- 4 files changed, 87 insertions(+), 84 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index e2a47cb..b74bdc1 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1,5 +1,7 @@ # This file is automatically @generated by Cargo. # It is not intended for manual editing. +version = 3 + [[package]] name = "bitflags" version = "1.2.1" @@ -235,6 +237,7 @@ version = "0.6.0" dependencies = [ "confy", "crossterm", + "lazy_static", "serde", "toml", "tui", diff --git a/Cargo.toml b/Cargo.toml index 33f3453..3e7d651 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -17,6 +17,7 @@ tui = { version = "0.14", default-features = false, features = ['crossterm'] } serde = {version = "1.0", features = ["derive"]} # confy = "0.4.0" toml = "0.4.2" +lazy_static = "1.4.0" [dependencies.confy] # TODO: Update this to v0.5.0 when it finally comes out -- for now, use latest git master diff --git a/src/calc.rs b/src/calc.rs index 1812acf..72b1e4f 100644 --- a/src/calc.rs +++ b/src/calc.rs @@ -1,4 +1,5 @@ pub mod entries; +use lazy_static::lazy_static; pub mod errors; pub mod operations; pub mod types; @@ -27,6 +28,79 @@ const APP_NAME: &str = "rpn_rs"; /// The default precision to sue const DEFAULT_PRECISION: usize = 3; +lazy_static! { + static ref OPERATION_MAP: HashMap = [ + ('+', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Add), + ), + ('-', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Subtract), + ), + ('*', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Multiply), + ), + ('/', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Divide), + ), + ('n', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Negate), + ), + ('|', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::AbsoluteValue), + ), + ('i', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Inverse), + ), + ('%', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Modulo), + ), + ('?', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::IntegerDivide), + ), + ('s', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Sin), + ), + ('c', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Cos), + ), + ('t', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Tan), + ), + ('S', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::ASin), + ), + ('C', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::ACos), + ), + ('T', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::ATan), + ), + ('v', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Sqrt), + ), + ('^', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Pow), + ), + ('l', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Log), + ), + ('L', CalculatorOperation::ArithmeticOperation( + ArithmeticOperation::Ln), + ), + // Temporary + ('V', CalculatorOperation::BuildVector), + ('M', CalculatorOperation::BuildMatrix), + ('_', CalculatorOperation::Deconstruct), + (')', CalculatorOperation::Transpose), + // Special + ('\\', CalculatorOperation::Drop), + (' ', CalculatorOperation::Dup), + ('>', CalculatorOperation::Swap), + ('u', CalculatorOperation::Undo), + ('U', CalculatorOperation::Redo), + ].iter().copied().collect(); +} + /// The history mode of the entry - either a single change or a macro bound #[derive(PartialEq, Debug, Serialize, Deserialize)] enum HistoryMode { @@ -115,13 +189,6 @@ impl Default for Calculator { value: String::from("RcRbRarbnrb2^4rarc**-v+2ra*/rbnrb2^4rarc**-v-2ra*/"), }, ), - ( - 't', - CalculatorMacro { - help: String::from("Testing"), - value: String::from("1 V1 "), - }, - ), ] .iter() .cloned() @@ -219,74 +286,6 @@ impl Calculator { } _ => Err(CalculatorError::ParseError), }, - '+' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Add, - )), - '-' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Subtract, - )), - '*' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Multiply, - )), - '/' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Divide, - )), - 'n' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Negate, - )), - '|' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::AbsoluteValue, - )), - 'i' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Inverse, - )), - '%' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Modulo, - )), - '?' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::IntegerDivide, - )), - 's' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Sin, - )), - 'c' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Cos, - )), - 't' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Tan, - )), - 'S' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::ASin, - )), - 'C' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::ACos, - )), - 'T' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::ATan, - )), - 'v' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Sqrt, - )), - '^' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Pow, - )), - 'l' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Log, - )), - 'L' => self.op(CalculatorOperation::ArithmeticOperation( - ArithmeticOperation::Ln, - )), - // Temporary - 'V' => self.op(CalculatorOperation::BuildVector), - 'M' => self.op(CalculatorOperation::BuildMatrix), - '_' => self.op(CalculatorOperation::Deconstruct), - ')' => self.op(CalculatorOperation::Transpose), - // Special - '\\' => self.op(CalculatorOperation::Drop), - ' ' => self.op(CalculatorOperation::Dup), - '>' => self.op(CalculatorOperation::Swap), - 'u' => self.op(CalculatorOperation::Undo), - 'U' => self.op(CalculatorOperation::Redo), // State modifiers 'm' => { self.state = CalculatorState::WaitingForMacro; @@ -308,7 +307,7 @@ impl Calculator { self.state = CalculatorState::WaitingForSetting; Ok(()) } - _ => Err(CalculatorError::NoSuchOperator(c)), + c => self.op(OPERATION_MAP.get(&c).ok_or(CalculatorError::NoSuchOperator(c))?), } } fn constant_input(&mut self, c: char) -> CalculatorResult<()> { @@ -333,7 +332,7 @@ impl Calculator { } // Record the macro started, if this is the outer macro - self.op(CalculatorOperation::Macro(MacroState::Start))?; + self.op(&CalculatorOperation::Macro(MacroState::Start))?; // Record that we are running macro c self.active_macros.insert(c); @@ -352,7 +351,7 @@ impl Calculator { self.active_macros.remove(&c); // Record the macro is over, if this is the outer macro - self.op(CalculatorOperation::Macro(MacroState::End))?; + self.op(&CalculatorOperation::Macro(MacroState::End))?; Ok(()) } @@ -432,7 +431,7 @@ impl Calculator { if !self.active_macros.is_empty() { self.active_macros.clear(); // Should always be successful, but report the error if there is one - self.op(CalculatorOperation::Macro(MacroState::End))?; + self.op(&CalculatorOperation::Macro(MacroState::End))?; } Ok(()) } @@ -604,7 +603,7 @@ impl Calculator { } /// Performs a calculator operation such as undo, redo, operator, or dup - pub fn op(&mut self, op: CalculatorOperation) -> CalculatorResult<()> { + pub fn op(&mut self, op: &CalculatorOperation) -> CalculatorResult<()> { // Dup is special -- don't actually run it if l needs to be flushed if self.flush_l()? { if let CalculatorOperation::Dup = op { @@ -693,7 +692,7 @@ impl Calculator { Ok(CalculatorStateChange { pop: OpArgs::None, - push: OpArgs::Macro(state), + push: OpArgs::Macro(*state), }) } }; diff --git a/src/calc/operations.rs b/src/calc/operations.rs index 6d59a54..1b30ee1 100644 --- a/src/calc/operations.rs +++ b/src/calc/operations.rs @@ -1,7 +1,7 @@ use super::entries::Entry; use serde::{Deserialize, Serialize}; -#[derive(PartialEq, Debug, Serialize, Deserialize)] +#[derive(PartialEq, Debug, Serialize, Deserialize, Copy, Clone)] pub enum ArithmeticOperation { Add, Subtract, @@ -24,7 +24,7 @@ pub enum ArithmeticOperation { Ln, } /// Operations that can be sent to the calculator such as +, -, or undo -#[derive(PartialEq, Debug, Serialize, Deserialize)] +#[derive(PartialEq, Debug, Serialize, Deserialize, Copy, Clone)] pub enum CalculatorOperation { ArithmeticOperation(ArithmeticOperation), BuildVector, @@ -40,7 +40,7 @@ pub enum CalculatorOperation { } /// Macro bundary; defined by the start or end of a macro invocation -#[derive(PartialEq, Debug, Serialize, Deserialize)] +#[derive(PartialEq, Debug, Serialize, Deserialize, Copy, Clone)] pub enum MacroState { Start, End,