From 682205f5e1ee589249df653637cb41599f1f3bf9 Mon Sep 17 00:00:00 2001 From: Mark Date: Mon, 4 Sep 2023 13:49:20 -0700 Subject: [PATCH] Fixed function evaluator --- src/evaluate/evaluate.rs | 2 +- src/evaluate/function.rs | 65 ++++++++++++++++++++-------------------- 2 files changed, 33 insertions(+), 34 deletions(-) diff --git a/src/evaluate/evaluate.rs b/src/evaluate/evaluate.rs index 4c46d95..d80109a 100644 --- a/src/evaluate/evaluate.rs +++ b/src/evaluate/evaluate.rs @@ -63,7 +63,7 @@ pub fn evaluate( context.get_variable(&s) }, - Expression::Operator(_, Operator::Function(_), _) => { Some(eval_function(g)?) }, + Expression::Operator(_, Operator::Function(_), _) => { eval_function(g)? }, Expression::Operator(_, _, _) => { eval_operator(context, g)? }, }; diff --git a/src/evaluate/function.rs b/src/evaluate/function.rs index 005523d..e24a391 100644 --- a/src/evaluate/function.rs +++ b/src/evaluate/function.rs @@ -26,7 +26,7 @@ fn to_radians(q: Quantity) -> Result { -pub fn eval_function(g: &Expression) -> Result { +pub fn eval_function(g: &Expression) -> Result, (LineLocation, DaisyError)> { let Expression::Operator(loc, Operator::Function(f), args) = g else {unreachable!()}; @@ -41,113 +41,112 @@ pub fn eval_function(g: &Expression) -> Result { return Ok(Expression::Quantity(*loc + *l, q.without_unit())); } - Function::ToBase => { return Ok(Expression::Quantity(*loc + *l, q.convert_to_base())); } + Function::NoUnit => { return Ok(Some(Expression::Quantity(*loc + *l, q.without_unit()))); } + Function::ToBase => { return Ok(Some(Expression::Quantity(*loc + *l, q.convert_to_base()))); } Function::Abs => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.abs())); + return Ok(Some(Expression::Quantity(*loc + *l, q.abs()))); }, Function::Floor => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.floor())); + return Ok(Some(Expression::Quantity(*loc + *l, q.floor()))); }, Function::Ceil => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.ceil())); + return Ok(Some(Expression::Quantity(*loc + *l, q.ceil()))); }, Function::Round => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.round())); + return Ok(Some(Expression::Quantity(*loc + *l, q.round()))); }, Function::NaturalLog => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.ln())); + return Ok(Some(Expression::Quantity(*loc + *l, q.ln()))); }, Function::TenLog => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.log10())); + return Ok(Some(Expression::Quantity(*loc + *l, q.log10()))); }, Function::Sin => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.sin())); + return Ok(Some(Expression::Quantity(*loc + *l, q.sin()))); }, Function::Cos => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.cos())); + return Ok(Some(Expression::Quantity(*loc + *l, q.cos()))); }, Function::Tan => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.tan())); + return Ok(Some(Expression::Quantity(*loc + *l, q.tan()))); }, Function::Csc => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.csc())); + return Ok(Some(Expression::Quantity(*loc + *l, q.csc()))); }, Function::Sec => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.sec())); + return Ok(Some(Expression::Quantity(*loc + *l, q.sec()))); }, Function::Cot => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.cot())); + return Ok(Some(Expression::Quantity(*loc + *l, q.cot()))); }, Function::Sinh => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.sinh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.sinh()))); }, Function::Cosh => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.cosh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.cosh()))); }, Function::Tanh => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.tanh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.tanh()))); }, Function::Csch => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.csch())); + return Ok(Some(Expression::Quantity(*loc + *l, q.csch()))); }, Function::Sech => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.sech())); + return Ok(Some(Expression::Quantity(*loc + *l, q.sech()))); }, Function::Coth => { let Ok(q) = to_radians(q.clone()) else { return Err((*loc + *l, DaisyError::IncompatibleUnit)); }; - return Ok(Expression::Quantity(*loc + *l, q.coth())); + return Ok(Some(Expression::Quantity(*loc + *l, q.coth()))); }, Function::Asin => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.asin())); + return Ok(Some(Expression::Quantity(*loc + *l, q.asin()))); }, Function::Acos => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.acos())); + return Ok(Some(Expression::Quantity(*loc + *l, q.acos()))); }, Function::Atan => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.atan())); + return Ok(Some(Expression::Quantity(*loc + *l, q.atan()))); }, Function::Asinh => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.asinh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.asinh()))); }, Function::Acosh => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.acosh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.acosh()))); }, Function::Atanh => { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} - return Ok(Expression::Quantity(*loc + *l, q.atanh())); + return Ok(Some(Expression::Quantity(*loc + *l, q.atanh()))); }, @@ -160,7 +159,7 @@ pub fn eval_function(g: &Expression) -> Result { let mut k = Quantity::new_rational(1f64).unwrap(); @@ -172,7 +171,7 @@ pub fn eval_function(g: &Expression) -> Result { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} @@ -181,7 +180,7 @@ pub fn eval_function(g: &Expression) -> Result { if !q.unitless() { return Err((*loc + *l, DaisyError::IncompatibleUnit));} @@ -191,7 +190,7 @@ pub fn eval_function(g: &Expression) -> Result