Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <iostream>
- #include <string>
- #include <cmath>
- // ..:: COMMAND ::..
- typedef void(*fptr)();
- struct Command
- {
- const char* name;
- fptr func;
- };
- // ..:: END COMMAND ::..
- // ..:: STACK ::..
- #define MAX_STACK_LENGTH 8
- struct Stack
- {
- int top;
- double* values;
- };
- // Initialize a stack
- void st_init(Stack* st)
- {
- st->top = -1;
- st->values = new double[MAX_STACK_LENGTH];
- }
- // Pop a top value from a stack
- void st_pop(Stack* st)
- {
- if (st->values == nullptr || st->top == -1)
- throw std::runtime_error("(st_top): The stack is empty");
- st->top--;
- }
- // Push a value into a stack's top
- void st_push(Stack* st, double value)
- {
- if (st->top + 1 < MAX_STACK_LENGTH)
- st->values[st->top++] = value;
- else
- throw std::runtime_error("(st_push): The stack is full");
- }
- // Get the top value from a stack
- double st_top(Stack* st)
- {
- if (st->top != -1)
- return st->values[st->top - 1];
- throw std::runtime_error("(st_top): The stack is empty");
- }
- // Replace the top value with the new one
- void st_replace(Stack* st, double value)
- {
- if (st->top == -1)
- throw std::runtime_error("(st_replace): The stack is empty");
- //std::cerr << "(st_replace): The stack is empty" << std::endl;
- st->values[st->top - 1] = value;
- }
- // Remove all values from a stack
- void st_clear(Stack* st)
- {
- st_free(st);
- st_init(st);
- }
- // Free the memory allocated for the stack values
- void st_free(Stack* st)
- {
- delete[] st->values;
- }
- // ..:: END STACK ::..
- // ..:: MAIN ::..
- // PI value
- #define M_PI 3.14159265358979323846
- static Stack* stack; // The main stack
- static bool in_runtime = true; // Is program still running
- // Clear the stack (remove all data)
- void fn_clear()
- {
- st_clear(stack);
- }
- // Print the top value from the stack
- void fn_print()
- {
- std::cout << st_top(stack) << std::endl;
- }
- // Quit the program
- void fn_quit()
- {
- in_runtime = false;
- }
- // Addition
- void op_add()
- {
- double a, b;
- a = st_top(stack);
- st_pop(stack);
- b = st_top(stack);
- st_pop(stack);
- st_push(stack, a + b);
- }
- // Subtraction
- void op_subtract()
- {
- double a, b;
- a = st_top(stack);
- st_pop(stack);
- b = st_top(stack);
- st_pop(stack);
- st_push(stack, b - a);
- }
- // Multiplication
- void op_multiply()
- {
- double a, b;
- a = st_top(stack);
- st_pop(stack);
- b = st_top(stack);
- st_pop(stack);
- st_push(stack, a * b);
- }
- // Division
- void op_divide()
- {
- double a, b;
- a = st_top(stack);
- st_pop(stack);
- b = st_top(stack);
- if (a == 0) throw std::runtime_error("Cannot divide by zero");
- st_pop(stack);
- st_push(stack, b / a);
- }
- // Sine function
- void fn_sin()
- {
- double a = st_top(stack);
- st_pop(stack);
- st_push(stack, std::sin(a));
- }
- // Cosine function
- void fn_cos()
- {
- double a = st_top(stack);
- st_pop(stack);
- st_push(stack, std::cos(a));
- }
- // Tangent function
- void fn_tan()
- {
- double a = st_top(stack);
- if (std::cos(a) == 0) throw std::runtime_error("Bad values for tan function (cos a = 0, division by zero)");
- st_pop(stack);
- st_push(stack, std::tan(a));
- }
- // Arctangent function
- void fn_atan()
- {
- double a = st_top(stack);
- st_pop(stack);
- st_push(stack, std::atan(a));
- }
- // Arcsine function
- void fn_asin()
- {
- double a = st_top(stack);
- if (a < -1 || a > 1) throw std::runtime_error("Bad values for asin function (a < -1 or a > 1)");
- st_pop(stack);
- st_push(stack, std::asin(a));
- }
- // Arccosine function
- void fn_acos()
- {
- double a = st_top(stack);
- if (a < -1 || a > 1) throw std::runtime_error("Bad values for acos function (a < -1 or a > 1)");
- st_pop(stack);
- st_push(stack, std::acos(a));
- }
- // PI constant
- void cn_pi()
- {
- st_push(stack, M_PI);
- }
- Command cmd[14] = {
- // Operators
- { "+", op_add },
- { "-", op_subtract },
- { "*", op_multiply },
- { "/", op_divide },
- // Functions
- { "clear", fn_clear },
- { "print", fn_print },
- { "quit", fn_quit },
- { "sin", fn_sin },
- { "cos", fn_cos },
- { "tan", fn_tan },
- { "atan", fn_atan },
- { "asin", fn_asin },
- { "acos", fn_acos },
- // Constants
- { "pi", cn_pi },
- };
- fptr get_function_by_name(const char* name)
- {
- for (int i = 0; i < 14; i++)
- if (strcmp(cmd[i].name, name) == 0)
- return cmd[i].func;
- throw std::runtime_error("No function with this name found");
- }
- int main()
- {
- stack = new Stack();
- st_init(stack);
- std::string last_cmd = "";
- do
- {
- std::cin >> last_cmd;
- try
- {
- if (isdigit(last_cmd[0]))
- {
- double value = std::stod(last_cmd.c_str());
- st_push(stack, value);
- }
- else
- get_function_by_name(last_cmd.c_str())();
- }
- catch (std::exception ex)
- {
- std::cerr << ex.what() << std::endl;
- }
- } while (in_runtime);
- st_free(stack);
- delete stack;
- return 0;
- }
- // ..:: END MAIN ::..
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement