-1

I'm having trouble with my code. it seems to work only on single digit int. I don't know how to create a function that would work for int greater than 9. Also I don't know how to end the program if string is empty.

Here's my code:

#include <stdio.h>
#include <stdlib.h> 
#include <string.h>
#include <ctype.h>

//stack type
struct node
{
    int head;
    int *array;
    unsigned capacity;
};

struct node* createNode();
int isEmpty();
char pop();
void push(struct node* stack, char op);
int evaluatePostfix();

int main()    {
    char exp[1000]; // = "5 1 2 + 4 * + 3 -";
    printf("Input string:\t");
    fgets(exp, 1000, stdin);
    for(int i = 1 ; i <= strlen(exp); i++) {
        if(exp[i] == '\n') {
            exp[i] = '\0';
        }
        else if (exp[0] == '\n') {
            printf("stack is empty\n");
            exit(0);
        }
    }
    printf ("%s = %d\n", exp, evaluatePostfix(exp));
    return 0;
}

struct node* createNode(unsigned capacity)  {
    struct node* stack = (struct node*) malloc(sizeof(struct node));

    if (!stack) return NULL;

    (*stack).head = -1;
    (*stack).capacity = capacity;
    (*stack).array = (int*) malloc((*stack).capacity *sizeof(int));

    if (!(*stack).array) return NULL;

    return stack;
}

int isEmpty(struct node *stack) {
    return (*stack).head == -1 ;
}


char pop(struct node* stack)    {
    if (!isEmpty(stack))
    return (*stack).array[(*stack).head--] ;
    return '$';
}


void push(struct node* stack, char op)  {
    (*stack).array[++(*stack).head] = op;
}

// The main function that returns value of a given postfix expression 
int evaluatePostfix(char* exp)  {

// Create a stack of capacity equal to expression size
    struct Stack* stack = createStack(strlen(exp));
    struct node *stack = createNode(strlen(exp));
    if (!stack) return -1;

// Scan all characters one by one

for (int i = 0; exp[i]; ++i){
    // If the scanned character is an operand or number,
    // push it to the stack.    
   if ((exp[i])== ' ') continue;
   else if (isdigit(exp[i]))
        push(stack, exp[i] - '0');


    //  If the scanned character is an operator, pop two
    // elements from stack apply the operator 
    else
    {
        int val1 = pop(stack);
        int val2 = pop(stack);
        switch (exp[i])
        {
         case '+': push(stack, val2 + val1); break;
         case '-': push(stack, val2 - val1); break;
         case '*': push(stack, val2 * val1); break;
         case '/': push(stack, val2/val1);   break;
        }
    }
}
return pop(stack);
}
Anthon
  • 69,918
  • 32
  • 186
  • 246

1 Answers1

0

I can't write the whole thing for you but can point you in the right direction. Firstly, when someone says "library function XYZ() would be helpful for you" then you should go and read about that function in the manual pages. For example, from a Linux shell run: man atoi to read about the atoi function.

For your particular problem, it boils down to parsing strings and converting them to numbers and operators. Some helpful library functions would thus be:

  • strtok: Extracts delimited string tokens from a longer string. You can use this to get each of the seperate inputs.
  • atoi: This can convert a string representation of a number to its integer equivalent. Does not allow for error checking.
  • strtol: Can do the same as atoi (and more) and also allows for error checking.

With that information in mind, here is a code snippet that may be useful for you:

int evaluatePostfix(char* exp)
{
    char *token;
    long int number;

    /* strtok will keep extracting the next token delimited by space */
    while (token = strtok(exp, " ")) {

        /* Now parse the token and process it */
        if (is_operator(token)) {
            /* do operator processing */
        } else {
            number = strtol(token, NULL, 10);
            /* do number processing */
        }
    }

    /* strtok returns NULL when no more tokens. So
       we are done when the while loop exits */
}

Note that the above code does not do error checking on strtol. You probably want to do that. Read the manual pages for strtol to understand how error checking is done for it.

kaylum
  • 13,833
  • 2
  • 22
  • 31