/* depend: */
/* cflags: */
-/* linker: atoi.o debug.o fdprintf.o parser.o */
+/* linker: atoi.o debug.o fdprintf.o parser.o -lm */
//#include <malloc.h>
#include <stddef.h>
VERBOSE (WARNING, PRINTOUT ("error while parsing: %s\n", buffer));
ret = 1;
} else {
- print_element (element, 0);
+ VERBOSE (INFO, print_element (element, 0));
+ PRINTOUT ("=> %f\n", evaluate_element (element));
ret = 0;
}
//fsync (stdfdout);
// test: calc.exe -h | awk '/usage:/ { rc=1 } END { exit (1-rc) }'
// test: calc.exe -_ 2> /dev/null | awk 'END { if (NR == 0) { exit(0) } else exit (1) }'
// test: calc.exe -_ 2>&1 | awk '/usage:/ { rc=1 } END { exit (1-rc) }'
-// test: echo "1 + 2" | calc.exe
-// test: echo "1 - 2" | calc.exe
-// test: echo "1 * 2" | calc.exe
-// test: echo "1 / 2" | calc.exe
-// test: echo "2 ^ 3" | calc.exe
-// test: echo "1e-1 + 2.34e5" | calc.exe
-// test: echo "sqrt (2)" | calc.exe
-// test: echo "pow (2, 3)" | calc.exe
-// test: echo "cos (2)" | calc.exe
-// test: echo "sin (2)" | calc.exe
-// test: echo "atan (2)" | calc.exe
-// test: echo "exp (2)" | calc.exe
-// test: echo "log (2)" | calc.exe
-// test: echo "1 + 2 - 3" | calc.exe
-// test: echo "1 + cos (2 - 3)" | calc.exe
-// test: echo "cos (1 / 2) * 3" | calc.exe
-// test: echo "1 + 4 * (2 - 3)" | calc.exe
-// test: echo "(2 - 3) / 4" | calc.exe
-// test: echo "pow (2 - 3, 8 / 3)" | calc.exe
-// test: echo "1 + -2" | calc.exe
-// test: echo "1 - +2" | calc.exe
-// test: echo "-1 + +2" | calc.exe
-// test: echo "-1+2" | calc.exe
-// test: echo "1-2" | calc.exe
-// test: echo "1 * 2 / 3 + 4" | calc.exe
-// test: echo "2 ^ 3 * 4 + 5" | calc.exe
-// test: echo "2 + 3 * 4 ^ 5" | calc.exe
-// test: echo "2 ^ 3 * 4 + cos(5/6)" | calc.exe
+// test: echo "1 + 2" | calc.exe | grep -q '=> 3'
+// test: echo "1 - 2" | calc.exe | grep -q '=> -1'
+// test: echo "2 * 3" | calc.exe | grep -q '=> 6'
+// test: echo "1 / 2" | calc.exe | grep -q '=> 5e-1'
+// test: echo "2 ^ 3" | calc.exe | grep -q '=> 8'
+// test: echo "1e-1 + 2.34e3" | calc.exe | grep -q '=> 2.3401'
+// test: echo "sqrt (2)" | calc.exe | grep -q '=> 1.414213'
+// test: echo "pow (2, 3)" | calc.exe | grep -q '=> 8'
+// test: echo "cos (2)" | calc.exe | grep -q '=> -4.161468e-1'
+// test: echo "sin (2)" | calc.exe | grep -q '=> 9.092974e-1'
+// test: echo "atan (2)" | calc.exe | grep -q '=> 1.107148'
+// test: echo "exp (2)" | calc.exe | grep -q '=> 7.389056'
+// test: echo "log (2)" | calc.exe | grep -q '=> 6.931471e-1'
+// test: echo "2 + 3 - 4" | calc.exe | grep -q '=> 1'
+// test: echo "1 + cos (2 - 3)" | calc.exe | grep -q '=> 1.54030'
+// test: echo "cos (1 / 2) * 3" | calc.exe | grep -q '=> 2.63274'
+// test: echo "1 + 4 * (2 - 3)" | calc.exe | grep -q '=> -3'
+// test: echo "(2 - 3) / 4" | calc.exe | grep -q '=> -2.5e-1'
+// test: echo "pow (8 - 3, 4 / 3)" | calc.exe | grep -q '=> 8.549879'
+// test: echo "1 + -2" | calc.exe | grep -q '=> -1'
+// test: echo "1 - +2" | calc.exe | grep -q '=> -1'
+// test: echo "-1 + +2" | calc.exe | grep -q '=> 1'
+// test: echo "-1+2" | calc.exe | grep -q '=> 1'
+// test: echo "1-2" | calc.exe | grep -q '=> -1'
+// test: echo "1 * 2 / 3 + 4" | calc.exe | grep -q '=> 4.666666'
+// test: echo "2 ^ 3 * 4 + 5" | calc.exe | grep -q '=> 3.7e1'
+// test: echo "2 + 3 * 4 ^ 5" | calc.exe | grep -q '=> 3.074e3'
+// test: echo "2 ^ 3 * 4 + cos(5/6)" | calc.exe | grep -q '=> 3.267241e1'
/* vim: set ts=4 sw=4 et: */
#include <malloc.h>
+#include <math.h>
#include <stdlib.h>
#include "debug.h"
switch (root->func) {
case Val: func = "Value"; break;
- case Set: func = "Set"; break;
case Add: func = "Addition"; break;
case Sub: func = "Subtraction"; break;
case Mul: func = "Multiplication"; break;
}
}
+/* evaluate element tree */
+
+double evaluate_element (element_t *root)
+{
+ double op0 = 0, op1 = 0;
+
+ if ((root == NULL) || (root == ERROR_OP)) {
+ VERBOSE (WARNING, PRINTOUT ("error while evaluating\n"));
+ return 0;
+ }
+
+ switch (root->func) {
+ case Val:
+ if (root->ops[0]) {
+ return evaluate_element (root->ops[0]);
+ } else {
+ return root->value;
+ }
+ break;
+ case Add:
+ case Sub:
+ case Mul:
+ case Div:
+ case Pow:
+ if (root->ops[1]) {
+ op1 = evaluate_element (root->ops[1]);
+ } else {
+ VERBOSE (WARNING, PRINTOUT ("error while evaluating (op[1])\n"));
+ return 0;
+ }
+ /* fallthrough */
+ case Sqr:
+ case Cos:
+ case Sin:
+ case Atn:
+ case Log:
+ case Exp:
+ if (root->ops[0]) {
+ op0 = evaluate_element (root->ops[0]);
+ } else {
+ VERBOSE (WARNING, PRINTOUT ("error while evaluating (op[0])\n"));
+ return 0;
+ }
+ }
+
+ switch (root->func) {
+ case Add: return op0 + op1;
+ case Sub: return op0 - op1;
+ case Mul: return op0 * op1;
+ case Div: return op0 / op1;
+ case Pow: return pow (op0, op1);
+ case Sqr: return sqrt (op0);
+ case Cos: return cos (op0);
+ case Sin: return sin (op0);
+ case Atn: return atan (op0);
+ case Log: return log (op0);
+ case Exp: return exp (op0);
+ default: break;
+ }
+
+ return 0;
+}
+
/* vim: set ts=4 sw=4 et: */