Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

START WITH THIS: #include <stdio.h> #include <stdlib.h> #include <assert.h> type

ID: 3575575 • Letter: S

Question

START WITH THIS:

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>

typedef struct node {
double value;
struct node *next;
} Stack;

void push( Stack *, double );
double pop( Stack * );
void show( Stack * );

int main(void)
{
Stack base, *top;

base.value = 0.0;
base.next = NULL;
top = &base;

push(top, 8);
push(top, 5);
push(top, 10);

show( top );
printf("%lf ", pop(top));
printf("%lf ", pop(top));
printf("%lf ", pop(top));
printf("%lf ", pop(top));
printf("%lf ", pop(top));
push(top, 20);
show( top );

return 0;
}

void show( Stack *top )
{
Stack *t;

assert( top != NULL );
t = top->next;
while( t != NULL ) {
printf("%lf ", t->value);
t = t->next;
}
}

void push( Stack *top, double newdata )
{
/*
* Stack function builds the dynamic stack below top, which
* must already exist as a node and is static.
*/
assert( top != NULL );
Stack *new;
if( (new = (Stack *)malloc(sizeof(Stack))) == NULL) {
printf( "Memory Allocation error. " );
return;
}
new->next = top->next;
new->value = newdata;
top->next = new;
}

double pop( Stack *top )
{
/*
* Stack function builds the dynamic stack below top, which
* must already exist as a node and is static.
*
* This pop() is a little different than what one might do in an OO
* implementation, such as with C++.
* The main reason for keeping the top of the stack static is to make it easy to maintain
* the new top of the stack and also to return the top data value that is
* popped or removed from the stack.
*/
double value;
Stack *tmp;
  
assert( top != NULL );
tmp = top->next;
if( tmp != NULL ) {
value = tmp->value;
top->next = tmp->next;
free( tmp );
return value;
}
else
return top->value;
}

QUESTION:

Write a program that works as a simple RPN (Reverse Polish Notation) calculator. RPN calculators work slightly different than normal calculators. Because they work on the model of a stack, it is never necessary to use parenthesis to express a mathematical equation, regardless of how complex the equation is. Many scientists, mathematicians and engineers consider RPN to be a much better model for using a calculator than the more common calculator model, which uses parenthesis and equal signs.

The main concept to understand about how RPN calculators work is that they use a stack (last in, first out) and postfix binomial operators. As new data is entered, it is pushed onto the top of the stack, pushing the previously entered data further down the stack. Binomial operators are entered in postfix manner after the two numbers have been entered. When an operator value is entered, the top two values on the stack are used to determine a result, which is stored at the top of stack.

To add the numbers 4 and 5 to get a sum of 9, with an infix calculator, one would enter:

On an RPN calculator, this would be expressed as:

When the [enter] key is pressed, the 4 is pushed onto the stack. The 5 is then put at the top of the stack. When the calculator processes the +, it takes the top two stack values (4 and 5) adds them together and stores a 9 at the top of the stack. Whatever is the top stack value is what is displayed on the screen.

Note

For the input of a computer to work exactly like a real calculator, the input would need to be processed in raw mode rather than the normal buffered, also called cooked, mode. We will not tackle that complexity for this problem, so for the above example, the keys pressed on the keyboard would need to be as follows:

Data should be read from the keyboard as strings. If the data entered is one of { +, -, *, /}, then the operation of add, subtract, multiply or divide should be performed on the top two stack values with the result being stored to the stack. Entered numeric data should be pushed onto the stack as a floating point number. Any other data (e.g., text characters), should be treated as a user error with an error message displayed. The special sentinel key of a grave accent ` should used to cause the program to exit.

The stack should be implemented using a linked list. Depending on your implementation, you may wish to implement the following functions before you can really begin implementing the calculator.

Based on code in the study guide, here is some code to get you started working with a stack. stack.c

Hint

Use the ReadLine function to reliably read in the data. (String Example - ReadLine)

It may simplify your programming if you use a fixed Stack data structure to always hold the top value. The next pointer of this top structure can point to the top of the actual stack.

See Example Use of strtod and strtol. You will want to use this example function to convert the string data to doubles and to determine if numeric data was entered or not.

Function Use void *push( Stack *, double ); Add a number to the top of the stack double pop( Stack * ); Return and remove the top stack item double get( Stack * ); Return the top stack item void replace(Stack *, double); Replace the top stack value void show( Stack * ); Display the top stack value

Explanation / Answer

//main.cpp

//ReadLine function declaration
void ReadLine(char str1[], char str2[], char *c);
int main(void)
{
   Stack base, *top;

   base.value = 0.0;
   base.next = NULL;
   top = &base;

  //add code for RPN here
   //declare two strings to read from input
   char str1[10];
   char str2[10];
   //declare integers to hold values for oparand1 and operand2
   double operand1, operand2;
   char operator1;

   //call read line function
   ReadLine(str1, str2, &operator1);
  
   //convert string to double
   operand1 = atof(str1);
   operand2 = atof(str2);
   //push parerands
   push(top,operand1);
   push(top,operand2);
   show(top);
   //depending on the operator perform operation
   switch (operator1)
   {
       //add two operands
   case '+':
           {
               double sum = pop(top) + pop(top);
               printf("Sum = %lf ", sum);
               break;
           }
   case '-':
           {
               double diff = pop(top) - pop(top);
               printf("Difference = %lf ", diff);
               break;
           }
   case '*':
           {
               double prod = pop(top) * pop(top);
               printf("Product = %lf ", prod);
               break;
           }
   case '/':
           {
               double quo = pop(top) / pop(top);
               printf("Quotient = %lf ", quo);
               break;
           }
   default:
           {
               printf("not valid operator ");
               break;
           }
                  
   }
   return 0;
}

//ReadLine
void ReadLine(char str1[], char str2[], char *c)
{
   char str[100];
   int i =0;
   int valid1= 1;
   int valid2 = 1;
   //Enter RPN expression
   printf("Enter RPN expression: ");
  
   fflush(stdin);
   fgets(str1, 100, stdin);
   //remove newline from string
   str1[strlen(str1) - 1] = '';
   fgets(str2, 100, stdin);
   //remove newline from string
   str2[strlen(str2) - 1] = '';
   *c = fgetc(stdin);
   return;
}

---------------------------------------------

output

Enter RPN expression:
5
4
+
4.000000
5.000000
Sum = 9.000000