#include #include #include typedef struct { double* st; int cnt; int size; } STACK; STACK* init_stack(int size) { if (size <= 0) { return NULL; } STACK *buf; buf = malloc(sizeof(STACK)); if (buf == NULL) { fprintf(stderr, "Error allocating structure\n"); return NULL; } buf -> st = malloc(sizeof(int)*size); if (buf -> st == NULL) { fprintf(stderr, "Error allocating array\n"); free(buf); return NULL; } buf -> cnt = 0; buf -> size = size; return buf; } void destroy_stack(STACK* s) { free(s -> st); free(s); } void push(STACK* st, double val) { if ((st -> cnt) < (st -> size)) { st -> st[st -> cnt] = val; (st -> cnt)++; } else { fprintf(stderr, "Stack is full! Stack size is %d, value to add is %f\n", st -> size, val); } } double pop(STACK* st) { if ((st -> cnt) > 0) { (st -> cnt)--; return st -> st[st -> cnt]; } else { fprintf(stderr, "Attempted to pop an empty stack\n"); return 0; } } void add(STACK* st) { if ((st -> cnt) > 1) { (st -> cnt)--; st -> st[(st -> cnt)-1] = st -> st[(st -> cnt)-1] + st -> st[st -> cnt]; } else { fprintf(stderr, "Not enough operands to add\n"); } } void substract(STACK* st) { if ((st -> cnt) > 1) { (st -> cnt)--; st -> st[(st -> cnt)-1] = st -> st[(st -> cnt)-1] - st -> st[st -> cnt]; } else { fprintf(stderr, "Not enough operands to substract\n"); } } void multiply(STACK* st) { if ((st -> cnt) > 1) { (st -> cnt)--; st -> st[(st -> cnt)-1] = st -> st[(st -> cnt)-1] * st -> st[st -> cnt]; } else { fprintf(stderr, "Not enough operands to multiply\n"); } } void divide(STACK* st) { if ((st -> cnt) > 1) { (st -> cnt)--; st -> st[(st -> cnt)-1] = st -> st[(st -> cnt)-1] / st -> st[st -> cnt]; } else { fprintf(stderr, "Not enough operands to divide\n"); } } int parse(char *s, STACK* stack) { double operand = 0; char *endptr; if ((*s == '-') && (*(s+1) == '\0')) { substract(stack); return 0; } else if (*s == '+') { add(stack); return 0; } else if (*s == '/') { if ((stack -> st[(stack -> cnt)-1]) == 0) { return -2; } divide(stack); return 0; } else if (*s == 'x') { multiply(stack); return 0; } errno = 0; operand = strtod(s, &endptr); if (errno != 0 || *endptr != '\0') return -1; push(stack, operand); return 0; } int main(int argc, char **argv) { STACK* operands = init_stack(argc); if (operands == NULL) { fprintf(stderr, "Error creating operand stack.\n"); return(2); } int error; while(*++argv) { error = parse(*argv, operands); if (error == -1) { fprintf(stderr, "Error parsing operand.\n"); return(1); } else if (error == -2) { fprintf(stderr, "Division by zero!"); return(2); } } int i; printf("Stack status:\n"); for (i = (operands -> cnt); i > 0; i--) printf("%f\n", pop(operands)); destroy_stack(operands); return 0; }