Add semantic of bool logic and comparisons + tests
This commit is contained in:
parent
285c054d37
commit
1dec4b3c4f
@ -6,6 +6,18 @@
|
||||
#include "include/memory.h"
|
||||
using namespace std;
|
||||
|
||||
bool bool_cast(EvalResult value) {
|
||||
if (holds_alternative<int>(value)) {
|
||||
return get<int>(value) != 0;
|
||||
}
|
||||
else if (holds_alternative<double>(value)) {
|
||||
return get<double>(value) != 0;
|
||||
}
|
||||
else {
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
EvalResult eval(Node &ast, Memory &memory) {
|
||||
if (holds_alternative<InnerNode>(ast)) {
|
||||
InnerNode node = get<InnerNode>(ast);
|
||||
@ -44,6 +56,59 @@ EvalResult eval(Node &ast, Memory &memory) {
|
||||
memory.remove_scope();
|
||||
return {};
|
||||
} break;
|
||||
case NodeType::Eq: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 == e2;
|
||||
} break;
|
||||
case NodeType::Neq: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 != e2;
|
||||
} break;
|
||||
case NodeType::Lor: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return bool_cast(e1) || bool_cast(e2);
|
||||
} break;
|
||||
case NodeType::Land: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return bool_cast(e1) && bool_cast(e2);
|
||||
} break;
|
||||
case NodeType::Neg: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
|
||||
return !bool_cast(e1);
|
||||
} break;
|
||||
case NodeType::Lt: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 < e2;
|
||||
} break;
|
||||
case NodeType::Gt: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 > e2;
|
||||
} break;
|
||||
case NodeType::Leq: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 <= e2;
|
||||
} break;
|
||||
case NodeType::Geq: {
|
||||
EvalResult e1 = eval(node.children[0], memory);
|
||||
EvalResult e2 = eval(node.children[1], memory);
|
||||
|
||||
return e1 >= e2;
|
||||
} break;
|
||||
case NodeType::Plus: {
|
||||
int e1 = get<int>(eval(node.children[0], memory));
|
||||
int e2 = get<int>(eval(node.children[1], memory));
|
||||
|
63
test/bool_logic.cpp
Normal file
63
test/bool_logic.cpp
Normal file
@ -0,0 +1,63 @@
|
||||
#include "include/test.h"
|
||||
|
||||
#include "../src/include/memory.h"
|
||||
#include "../src/include/tokenize.h"
|
||||
#include "../src/include/parser.h"
|
||||
#include "../src/include/interpreter.h"
|
||||
|
||||
int execute(string s) {
|
||||
Memory memory = Memory();
|
||||
vector<Token> tokens = tokenize({ s });
|
||||
Node ast = parse(tokens);
|
||||
EvalResult res = eval(ast, memory);
|
||||
|
||||
return get<int>(res);
|
||||
}
|
||||
|
||||
int main() {
|
||||
_TEST_PRESENTATION("Logique Booléenne");
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("1 && 0;") == 0),
|
||||
"Et",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("1 || 0;") == 1),
|
||||
"Ou",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("!1;") == 0),
|
||||
"Négation",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 == 2;") == 1),
|
||||
"Égalité",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 != 2;") == 0),
|
||||
"Différence",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("0 == 0 || 1;") == 1),
|
||||
"Parenthésage",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 == 1 + 1;") == 1),
|
||||
"Priorités",
|
||||
true
|
||||
);
|
||||
|
||||
return 0;
|
||||
}
|
@ -25,7 +25,7 @@ int main() {
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("12 - 4 - 20;") == -12),
|
||||
"Ordre de soustraction",
|
||||
"Parenthésage",
|
||||
true
|
||||
);
|
||||
|
||||
@ -36,13 +36,13 @@ int main() {
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_IS_EXCEPTION(execute("1 / (5 - 5);"), RuntimeError),
|
||||
_TEST_IS_EXCEPTION(execute("1 / 0;"), RuntimeError),
|
||||
"Division par 0",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_IS_EXCEPTION(execute("1 % (5 - 5);"), RuntimeError),
|
||||
_TEST_IS_EXCEPTION(execute("1 % 0;"), RuntimeError),
|
||||
"Modulo par 0",
|
||||
true
|
||||
);
|
||||
@ -65,5 +65,29 @@ int main() {
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("1 < 2;") == 1),
|
||||
"Inférieur strict",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 > 3;") == 0),
|
||||
"Supérieur strict",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 <= 1;") == 0),
|
||||
"Inférieur ou égal",
|
||||
true
|
||||
);
|
||||
|
||||
_TEST_ASSERT(
|
||||
_TEST_NO_EXCEPTION(execute("2 >= 1;") == 1),
|
||||
"Supérieur ou égal",
|
||||
true
|
||||
);
|
||||
|
||||
return 0;
|
||||
}
|
@ -109,7 +109,7 @@ int main() {
|
||||
false
|
||||
)
|
||||
|
||||
_TEST_ASSERT(true, "+++", true)
|
||||
_TEST_ASSERT(true, "Triple plus", true)
|
||||
}
|
||||
|
||||
/* Incorrect input */
|
||||
|
Loading…
Reference in New Issue
Block a user