Thread: Evaluating an Expression

  1. #1
    Registered User
    Join Date
    Mar 2003
    Posts
    24

    Evaluating an Expression

    This compiles and runs correctly, but it says "The value is 0" Am I not returning what I should be?

    Thanks for any help

    Code:
    #include <stdio.h>        
    #include <string.h>
    #include <stdlib.h>
    #include <ctype.h>
    
    #define FAILED -1;
    
    typedef struct node stack;
    typedef stack * stack_ptr;
    struct node
    {                             
       int key;             
       stack_ptr next; 
    }; 
    
    int evaluate(char *);
    int isempty(stack_ptr);
    void push(stack_ptr *, int);
    int pop(stack_ptr *);
    void cleanup(stack_ptr *);
    void print(stack_ptr);
    
    int main()
    {
     char str[80];
     int res;
     stack_ptr top = NULL;
    
       printf("Enter the postfix form expression:\n");
       gets(str);
    
       res = evaluate(str);
       printf("the result is %d: \n", res);
    
       return (0);
    }
    
    int evaluate(char *str)
    {
     int num=0;
     char ch=0;
     stack_ptr top = NULL;
    
    
       while((ch == *str))
       {
          num;
          if (ch == ' ') 
          {
             str++;
             continue;
          }
    
          if (ch == '+')
             num = pop(&top) + pop(&top);
          else
             if (ch == '*')
                num = pop(&top) * pop(&top);
             else
                while (1) 
                {
                   if (isdigit(ch))
                   {
                      num = 10*num + (ch -'0');
                      ch = *++str;
                   } 
                   else
                      if (ch == ' ') 
                         break;
                      else
                      {
                         printf("wrong input!\n");
                         exit (0);
                      }
                }
                push(&top, num);
                str++;
       }
       return num;
    }
    
    
    int isempty(stack_ptr top)
    {
       return (top == NULL);
    }
    
    void push(stack_ptr *top, int v)
    {
     stack_ptr tmp;
    
       tmp = (stack_ptr) malloc(sizeof(stack));
       if (tmp == NULL)
       {
          printf("Out of space!\n");
          exit (0);
       }
    
       tmp->key = v;
       tmp->next = *top;
       *top = tmp;
    }
    
    int pop(stack_ptr *top)
    {
     stack_ptr tmp;
     int x;
    
       if (isempty(*top)) 
       {
          printf("wrong input!\n");
          exit (1);
       }
    
       tmp = *top;
       x = tmp->key;
       *top = tmp->next;
    
       free(tmp);
       return x;
    }
    
    
    void cleanup(stack_ptr *top)
    {
     stack_ptr tmp;
    
       while(*top != NULL )
       {
          tmp = (*top)->next;
          free(*top);
          *top = tmp;  
       }
    }
    
    void print(stack_ptr top)
    {
     stack_ptr tmp =top;
    
       if (top != NULL)
          while (tmp != NULL) 
          {
             printf("\tvalue is %d\n",tmp->key);
             tmp = tmp->next;
          } 
       else
          printf("stack is empty\n");
    }

  2. #2
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    In the function evaluate() you initialize top = NULL. You then try to reference the address of this pointer before you give it an actual address.
    Code:
     stack_ptr top = NULL;
    
    
       while((ch == *str))
       {
          num;
          if (ch == ' ') 
          {
             str++;
             continue;
          }
    
          if (ch == '+')
             num = pop(&top) + pop(&top);
          else
             if (ch == '*')
                num = pop(&top) * pop(&top);

  3. #3
    Registered User
    Join Date
    Mar 2003
    Posts
    24
    What should top be set to?

  4. #4
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    And if there are any other issues, (that was the first i noticed), please put some comments in the code.

  5. #5
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    I dont know, lol, thats what you should know, it points to nothing right now (NULL), it needs to point to the beginning of a struct. You declared it that way, to point to struct data type.

  6. #6
    char main() RoshanX's Avatar
    Join Date
    Mar 2003
    Posts
    68
    I have modified your code. You have some errors in your code. Some of the changed that I have made, I've put a commnet.

    Code:
    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include <ctype.h>
    
    #define FAILED -1;
    
    typedef struct node stack;
    typedef stack * stack_ptr;
    struct node
    {
       int key;
       stack_ptr next;
    };
    
    int evaluate(char *);
    int isempty(stack_ptr);
    void push(stack_ptr *, int);
    int pop(stack_ptr *);
    void cleanup(stack_ptr *);
    void print(stack_ptr);
    
    int main()
    {
     char str[80];
     int res;
     stack_ptr top = NULL;   // not required 
    
       printf("Enter the postfix form expression:\n");
       gets(str);
    
       res = evaluate(str);
       printf("the result is %d: \n", res);
    
       return (0);
    }
    
    int evaluate(char *str)
    {
     int num=0;
     char ch=0;
     stack_ptr top = NULL;
    
    
       while((ch = *str))
       {
          num=0;       //CHANGED
          if (ch == ' ')
          {
    	 str++;
    	 continue;
          }
    
          if (ch == '+')
    	 num = pop(&top) + pop(&top);
          else
    	 if (ch == '*')
    	    num = pop(&top) * pop(&top);
    	 else
    	    while (1)
    	    {
    	       if (isdigit(ch))
    	       {
    		  num = 10*num + (ch -'0');
    		  ch = *(++str);     //changed 
    	       }
    	       else
    		  if (ch == ' ')
    		     break;
    		  else
    		  {
    		     printf("wrong input!\n");
    		     exit (0);
    		  }
    	    }
    	    push(&top, num);
    	    str++;
       }
       return num;
    }
    
    
    int isempty(stack_ptr top)
    {
       return (top == NULL);
    }
    
    void push(stack_ptr *top, int v)
    {
     stack_ptr tmp;
    
       tmp = (stack_ptr) malloc(sizeof(stack));
       if (tmp == NULL)
       {
          printf("Out of space!\n");
          exit (0);
       }
    
       tmp->key = v;
       tmp->next = *top;
       *top = tmp;
    }
    
    int pop(stack_ptr* top)
    {
     stack_ptr tmp;
     int x;
    
       if (isempty(*top))
       {
          printf("wrong input!\n");
          exit (1);
       }
    
       tmp = *top;
       x = tmp->key;
       *top = tmp->next;
    
       free(tmp);
       return x;
    }
    
    
    void cleanup(stack_ptr *top)
    {
     stack_ptr tmp;
    
       while(*top != NULL )
       {
          tmp = (*top)->next;
          free(*top);
          *top = tmp;
       }
    }
    
    void print(stack_ptr top)
    {
     stack_ptr tmp =top;
    
       if (top != NULL)
          while (tmp != NULL)
          {
    	 printf("\tvalue is %d\n",tmp->key);
    	 tmp = tmp->next;
          }
       else
          printf("stack is empty\n");
    }

  7. #7
    char main() RoshanX's Avatar
    Join Date
    Mar 2003
    Posts
    68
    The major error in your code was,

    Code:
     while((ch == *str))
    It sould be corrected as,

    Code:
     while((ch = *str))

  8. #8
    Registered User
    Join Date
    Mar 2003
    Posts
    24
    I've tried that in the past, and it says "Wrong input!"

    I've also heard from a few people that I should change it to:

    Code:
      while((ch == *str))
    I've also corrected the beginning of my evaluate function so it drops into my while loop:

    Code:
    int evaluate(char *str)
    {
     int num=0;
     char ch = *str;
     stack_ptr top = NULL;

  9. #9
    char main() RoshanX's Avatar
    Join Date
    Mar 2003
    Posts
    68
    I think the way you enter the expression is wrong. According to your program, (not the best way mind you ....) an expression is like this
    Code:
     NUMBER<space>NUMBER<space>OPERATOR
    for example,
    Code:
    3 4 +
    You could imporve on this.

    Aoubt the following while condition ,
    Code:
    while((ch == *str))
    This is wrong. It won't serve your purpose. What it will do is just compare "ch" with "*str". What you want to do is assign the value of "*str" to "ch" and continue the loop till NULL Is reached.
    so your code should be like this.

    Code:
    while((ch = *str))

  10. #10
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    I am sorry, but let me reiterate what i said in the first reply. When the heck are you going to assign top to something, you use the address here, but nevre initialize it but to NULL!
    Code:
    int evaluate(char *str)
    {
     int num=0;
     char ch=0;
     stack_ptr top = NULL;
    
    
       while((ch = *str))
       {
          num=0;       //CHANGED
          if (ch == ' ')
          {
    	 str++;
    	 continue;
          }
    
          if (ch == '+')
    	 num = pop(&top) + pop(&top); //you need to initialize to something other than NULL before you reference the address.
          else
    	 if (ch == '*')
    	    num = pop(&top) * pop(&top); //you need to initialize to something other than NULL before you reference the address.
    	 else
    	    while (1)
    	    {
    	       if (isdigit(ch))
    	       {
    		  num = 10*num + (ch -'0');
    		  ch = *(++str);     //changed 
    	       }
    	       else
    		  if (ch == ' ')
    		     break;
    		  else
    		  {
    		     printf("wrong input!\n");
    		     exit (0);
    		  }
    	    }
    	    push(&top, num);
    	    str++;
       }
       return num;
    }

  11. #11
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    Maybe if you try what he was suggesting with the = instead of ==, and assign top to what ever it needs to be, you wont get "Wrong input" becuase pop() will actually be able to use the address!!!

  12. #12
    char main() RoshanX's Avatar
    Join Date
    Mar 2003
    Posts
    68
    Here the statment

    Code:
    stack_ptr top = NULL;
    is to say that the stack is empty. This is not a problem. It has to be NULL initially because the stack is empty.

  13. #13
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    Thats fine if he wants to initialize to NULL. Check out the function pop() though. If he does that and doesn't change that value later on, it will always return "Wrong Input" which he says it is doing. He calls the pop() function and passes the address of the pointer which points to NULL. He needed to set that pointer to point to something else rather than NULL. It then should do more than its doing.
    I've tried that in the past, and it says "Wrong input!"
    This is what happens is you fallow the code. That NULL pointer i mentioned is passed to the pop() function. it then in turn calls the isempty() function and returns TRUE ***return (top == NULL) is TRUE***, which in turn is true to the if statement in the pop() function, so the if statement will run and and print out "Wrong inpput" and the pop() function will exit(1);
    Last edited by stumon; 03-31-2003 at 11:18 PM.

  14. #14
    char main() RoshanX's Avatar
    Join Date
    Mar 2003
    Posts
    68
    It gives the message "WRONG INPUT" because it's wrong input. There is nothing to argue there. If you check the code, first it will check to see if CH is "+" or "*" if so , it will pop the first two items from the stack. IF the correct POSTFIX was given, by the time an OPERATOR is reached, there should be operands in the stack. Say if you give an expression like ,
    Code:
    +34 45
    This will give a wrong input , as it should be, since first it encounters a "+" sign , tried to pop the stack, the stack is empty, so "WRONG INPUT".

    The reason he is getting this message is because it is a wroing input. The statment,
    Code:
    stack_ptr top = NULL;
    is not wrong.

  15. #15
    eh ya hoser, got a beer? stumon's Avatar
    Join Date
    Feb 2003
    Posts
    323
    The reason he is getting this message is because it is a wroing input. The statment,

    Code:
    stack_ptr top = NULL;
    is not wrong.
    I never said it was wrong, he can initialize it to NULL if he wants to, the problem is no where in the evaluate(), push(), or pop() function is it changed to point to something of value. He is trying to push, and pop the address of a pointer that points to NULL. Answer one question for me, how would he point that pointer to something? Answer: He would have to put this somewhere top = &something. Correct? Look at every single line of code, he mallocs memory like he sould, but never actually points top to anything. He always dereferences it but never assigns it to anything but NULL. How is it going to work if he doesn't assign top to anything?
    The keyboard is the standard device used to cause computer errors!

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Help with making a Math Expression DLL
    By MindWorX in forum C Programming
    Replies: 19
    Last Post: 07-19-2007, 11:37 PM
  2. Screwy Linker Error - VC2005
    By Tonto in forum C++ Programming
    Replies: 5
    Last Post: 06-19-2007, 02:39 PM
  3. recursion error
    By cchallenged in forum C Programming
    Replies: 2
    Last Post: 12-18-2006, 09:15 AM
  4. Please Help - Problem with Compilers
    By toonlover in forum C++ Programming
    Replies: 5
    Last Post: 07-23-2005, 10:03 AM
  5. evaluating unary negation operator in an infix expression??
    By YevGenius in forum C++ Programming
    Replies: 7
    Last Post: 05-12-2004, 01:18 PM