Implements binary operation for floats
This commit is contained in:
parent
d949d9aa8f
commit
e648013e1d
|
@ -1,4 +1,77 @@
|
|||
|
||||
#include "../Script.hpp"
|
||||
#include "EvaluationException.hpp"
|
||||
#include "Evaluator.hpp"
|
||||
|
||||
long Evaluator::EvaluateIntegerBinary(BoundBinaryExpression *expression) {
|
||||
long leftValue = this -> EvaluateIntegerExpression(expression->GetLeft());
|
||||
long rightValue = this -> EvaluateIntegerExpression(expression->GetRight());
|
||||
|
||||
switch (expression->GetOperation()){
|
||||
case BoundBinaryOperation ::Addition: return leftValue + rightValue;
|
||||
case BoundBinaryOperation ::Subtraction: return leftValue - rightValue;
|
||||
case BoundBinaryOperation ::Multiplication: return leftValue * rightValue;
|
||||
case BoundBinaryOperation ::Division: return leftValue / rightValue;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to integer");
|
||||
}
|
||||
}
|
||||
|
||||
double EvaluateBinaryOperation(double l, double r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
|
||||
double EvaluateBinaryOperation(double l, long r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
|
||||
double EvaluateBinaryOperation(long l, double r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
|
||||
double Evaluator::EvaluateFloatBinary(BoundBinaryExpression *expression) {
|
||||
auto left = expression->GetLeft();
|
||||
auto right = expression->GetRight();
|
||||
auto leftType = (NumericScriptType*)left->GetType();
|
||||
auto rightType = (NumericScriptType*)right->GetType();
|
||||
if (leftType->IsFloat()){
|
||||
double leftValue = this -> EvaluateFloatExpression(left);
|
||||
if (rightType->IsFloat()){
|
||||
double rightValue = this -> EvaluateFloatExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
} else{
|
||||
long rightValue = this -> EvaluateIntegerExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
}
|
||||
} else{
|
||||
long leftValue = this-> EvaluateIntegerExpression(left);
|
||||
// If the left is an integer, we know the right must be a float, otherwise we'd be evaluating as integer;
|
||||
double rightValue = this -> EvaluateFloatExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
}
|
||||
}
|
|
@ -1,7 +1,6 @@
|
|||
|
||||
#include "Evaluator.hpp"
|
||||
#include "EvaluationException.hpp"
|
||||
#include "BinaryEvaluation.cpp"
|
||||
#include "../Script.hpp"
|
||||
|
||||
void Evaluator::Evaluate(BoundScriptStatement *statement) {
|
||||
|
@ -68,7 +67,24 @@ long Evaluator::EvaluateIntegerExpression(BoundExpression *expression) {
|
|||
}
|
||||
|
||||
double Evaluator::EvaluateFloatExpression(BoundExpression *expression) {
|
||||
return 0;
|
||||
auto exprType = expression->GetType();
|
||||
if (exprType->GetClass() != TypeClass::Number){
|
||||
throw EvaluationException("Can't evaluate expression as float, it will not return a number.");
|
||||
}
|
||||
auto numType = (NumericScriptType*)exprType;
|
||||
if (numType->IsAwareOfFloat() && !numType->IsFloat()){
|
||||
throw EvaluationException("Can't evaluate expression as integer, it will return an integer, not a float.");
|
||||
}
|
||||
switch (expression->GetKind()){
|
||||
case BoundExpressionKind ::LiteralFloat: return ((BoundLiteralIntegerExpression*)expression)->GetValue();
|
||||
case BoundExpressionKind ::Binary: return this -> EvaluateFloatBinary((BoundBinaryExpression*)expression);
|
||||
|
||||
case BoundExpressionKind ::LiteralInteger:
|
||||
case BoundExpressionKind ::LiteralString:
|
||||
case BoundExpressionKind ::LiteralBool:
|
||||
case BoundExpressionKind ::Bad:
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
bool Evaluator::EvaluateBoolExpression(BoundExpression *expression) {
|
||||
|
@ -79,73 +95,3 @@ std::string Evaluator::EvaluateStringExpression(BoundExpression *expression) {
|
|||
return std::__cxx11::string();
|
||||
}
|
||||
|
||||
long Evaluator::EvaluateIntegerBinary(BoundBinaryExpression *expression) {
|
||||
long leftValue = this -> EvaluateIntegerExpression(expression->GetLeft());
|
||||
long rightValue = this -> EvaluateIntegerExpression(expression->GetRight());
|
||||
|
||||
switch (expression->GetOperation()){
|
||||
case BoundBinaryOperation ::Addition: return leftValue + rightValue;
|
||||
case BoundBinaryOperation ::Subtraction: return leftValue - rightValue;
|
||||
case BoundBinaryOperation ::Multiplication: return leftValue * rightValue;
|
||||
case BoundBinaryOperation ::Division: return leftValue / rightValue;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to integer");
|
||||
}
|
||||
}
|
||||
|
||||
double EvaluateBinaryOperation(double l, double r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
double EvaluateBinaryOperation(double l, long r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
double EvaluateBinaryOperation(long l, double r, BoundBinaryOperation op){
|
||||
switch (op){
|
||||
case BoundBinaryOperation ::Addition: return l + r;
|
||||
case BoundBinaryOperation ::Subtraction: return l - r;
|
||||
case BoundBinaryOperation ::Multiplication: return l * r;
|
||||
case BoundBinaryOperation ::Division: return l / r;
|
||||
|
||||
default:
|
||||
throw EvaluationException("Can't evaluate operation to float");
|
||||
}
|
||||
}
|
||||
|
||||
double Evaluator::EvaluateFloatBinary(BoundBinaryExpression *expression) {
|
||||
auto left = expression->GetLeft();
|
||||
auto right = expression->GetRight();
|
||||
auto leftType = (NumericScriptType*)left->GetType();
|
||||
auto rightType = (NumericScriptType*)right->GetType();
|
||||
if (leftType->IsFloat()){
|
||||
double leftValue = this -> EvaluateFloatExpression(left);
|
||||
if (rightType->IsFloat()){
|
||||
double rightValue = this -> EvaluateFloatExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
} else{
|
||||
long rightValue = this -> EvaluateIntegerExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
}
|
||||
} else{
|
||||
long leftValue = this-> EvaluateIntegerExpression(left);
|
||||
// If the left is an integer, we know the right must be a float, otherwise we'd be evaluating as integer;
|
||||
double rightValue = this -> EvaluateFloatExpression(right);
|
||||
return EvaluateBinaryOperation(leftValue, rightValue, expression->GetOperation());
|
||||
}
|
||||
}
|
|
@ -2,11 +2,61 @@
|
|||
#include <catch.hpp>
|
||||
#include "../src/Script.hpp"
|
||||
|
||||
TEST_CASE( "Simple addition", "[integration]" ) {
|
||||
TEST_CASE( "Integer Addition", "[integration]" ) {
|
||||
Script script = Script::Create("1 + 5");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<long>(lastValue) == 6);
|
||||
}
|
||||
TEST_CASE( "Integer Subtraction", "[integration]" ) {
|
||||
Script script = Script::Create("1 - 5");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<long>(lastValue) == -4);
|
||||
}
|
||||
TEST_CASE( "Integer Multiplication", "[integration]" ) {
|
||||
Script script = Script::Create("5 * 8");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<long>(lastValue) == 40);
|
||||
}
|
||||
TEST_CASE( "Integer Division", "[integration]" ) {
|
||||
Script script = Script::Create("40 / 8");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<long>(lastValue) == 5);
|
||||
}
|
||||
|
||||
TEST_CASE( "Float Addition", "[integration]" ) {
|
||||
Script script = Script::Create("1.2 + 5.34");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<double>(lastValue) == 6.54);
|
||||
}
|
||||
TEST_CASE( "Float Subtraction", "[integration]" ) {
|
||||
Script script = Script::Create("1.8 - 5.14");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<double>(lastValue) == -3.34);
|
||||
}
|
||||
TEST_CASE( "Float Multiplication", "[integration]" ) {
|
||||
Script script = Script::Create("5.2 * 8.9");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<double>(lastValue) == 46.28);
|
||||
}
|
||||
TEST_CASE( "Float Division", "[integration]" ) {
|
||||
Script script = Script::Create("95.18 / 8.87");
|
||||
REQUIRE(!script.Diagnostics -> HasErrors());
|
||||
script.Evaluate();
|
||||
auto lastValue = script.GetLastValue();
|
||||
REQUIRE(*any_cast<double>(lastValue) == Approx(10.730));
|
||||
}
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue