1use crate::errors::Error;
2use crate::eval::Eval;
3use crate::parse::Parser;
4
5pub struct Calculator {
7 parser: Parser,
8 eval: Eval,
9}
10
11impl Calculator {
12 pub fn new() -> Self {
14 Self {
15 parser: Parser::new(),
16 eval: Eval::new(),
17 }
18 }
19
20 pub fn calculate_line(&self, input: &str) -> Result<f64, Error> {
22 self.parser
23 .parse_line(input)
24 .and_then(|exp| self.eval.eval(&exp))
25 }
26}
27
28impl Default for Calculator {
29 fn default() -> Self {
30 Calculator::new()
31 }
32}
33
34#[cfg(test)]
35mod tests {
36 use super::*;
37 use crate::errors::EvalError;
38
39 #[test]
40 fn calculate_line() {
41 let c = calculator();
42
43 assert_eq!(c.calculate_line("1 + 2"), Ok(3.));
44 assert_eq!(c.calculate_line("-2 * -2"), Ok(4.));
45 }
46
47 #[test]
48 fn divide_by_zero() {
49 let c = calculator();
50
51 assert_eq!(
52 c.calculate_line("1 / 0"),
53 Err(Error::Eval(EvalError::ZeroDivision))
54 );
55 }
56
57 fn calculator() -> Calculator {
58 Calculator::new()
59 }
60}