CS 1723 -- Exercise 3
Translate Arithmetic Expressions to RPN
Due Monday, 15 October 2001


For this exercise you are to write a program that translates arithmetic expressions into RPN notation. The expressions have infix binary operators with the following precedence table:

OperatorsPrecedence
^ (raise to power)3 (highest)
*   /2 (middle)
+   -1 (lowest)

The only operands are single-digit numbers (to keep the programming simpler).

As part of the translator, you should use the Java class that you wrote for exercise 2 to evaluate the RPN, so that altogether you get an evaluator of arithmetic expressions.

As before, you should finish the details of the program below that again uses the Java Stack class -- this time as a stack of chars.

Here is the translation algorithm from the Week 6 Lecture notes.


Rules to translate an arithmetic expression to RPN:
    Rules for each input char (go on to next input char unless otherwise stated)
    Fetch next char, call it ch
  1. if ch is an operand, move it to output.
    From now on ch is an operator or '(' or ')'.
  2. if stack is empty, add ch to stack.
  3. if ch is '(', add ch to stack.
    From now on, stack is not empty. Use top for its top char (just peeked at, not popped).
  4. if ch is ')', remove chars from stack and output down to '(' on stack, which is thrown away.
  5. if top is '(', add ch to stack. From now on, both ch and top are regular operators.
  6. if prec(ch) > prec(top), add ch to stack.
  7. if prec(ch) < prec(top), move top to output, and DO NOT MOVE ON TO NEXT INPUT CHAR.
  8. if prec(ch) == prec(top) and left-to-right associativity, move top to output, and DO NOT MOVE ON TO NEXT INPUT CHAR.
  9. if prec(ch) == prec(top) and right-to-left associativity, add top to stack.
  10. at end, move everything on stack to output.

  • As before, here is a framework for this exercise. (You may rewrite or ignore this framework if you wish.)
    // Trans: translate input arith expr to RPN string
    import java.util.*;
    public class Trans { 
    
       Stack stack; // java library stack of objects, use for chars
       public Trans() {
          stack = new Stack();
       }
    
       // translate: an arith expr to RPN
       public String translate(String s) {
          // Supply code here to implement the above algorithm.
          // This is similar in many ways to the previous exercise.
          // You can use the two functions below if you wish.
       }
    
       // prec: return int precedence of operators
       private int prec(char ch) {
          switch (ch) {
             case '+': case '-': return 1;
             case '*': case '/': return 2;
             case '^': return 3;
             default: return -1;
          }
       }
    
       // assoc: return 'l' for left-to-right, and 'r' for right-to-left
       private char assoc(char ch) {
          switch (ch) {
             case '+': case '-': case '*': case '/': return 'l';
             case '^': return 'r';
             default: return '?';
          }
       }
    
       public static void main(String[] args) {
          GetNext getNext = new GetNext(); // input class
          Trans trans = new Trans(); // new translater
          Eval eval = new Eval(); // new evaluator
          // read and translate indefinitely
          String s = getNext.getNextString(); // fetch string
          System.out.println("Input: " + s);
          String resStr = trans.translate(s); // produce RPN
          System.out.println("RPN string: " + resStr); // print RPN
          double res = eval.evaluateRPN(resStr);
          System.out.println("Value: " + res); // print value
       }
    }
    

  • Here is sample output from the version of the program that I wrote. (Your output might look different, but you should have the same answers.) Input below is in boldface.
    2+3*4
    Input: 2+3*4
    RPN string: 234*+
    Value: 14.0

    2*3+4 Input: 2*3+4 RPN string: 23*4+ Value: 10.0

    2^3^4 Input: 2^3^4 RPN string: 234^^ Value: 2.4178516392292583E24

    2*(3+4) Input: 2*(3+4) RPN string: 234+* Value: 14.0

    2+(3*4) Input: 2+(3*4) RPN string: 234*+ Value: 14.0

    ((2)+(((3))))*((((4)))) Input: ((2)+(((3))))*((((4)))) RPN string: 23+4* Value: 20.0

    2+3*4^5*6+7 Input: 2+3*4^5*6+7 RPN string: 2345^*6*+7+ Value: 18441.0

    2^3*4+5*6^7 Input: 2^3*4+5*6^7 RPN string: 23^4*567^*+ Value: 1399712.0 2-3-4 Input: 2-3-4 RPN string: 23-4- Value: -5.0

    2/3/4 Input: 2/3/4 RPN string: 23/4/ Value: 0.16666666666666666

    2+3*4^5 Input: 2+3*4^5 RPN string: 2345^*+ Value: 3074.0

    2^3*4+5 Input: 2^3*4+5 RPN string: 23^4*5+ Value: 37.0

    2+3*4^5+6 Input: 2+3*4^5+6 RPN string: 2345^*+6+ Value: 3080.0

    3+1/(7+1/(5*3+1/(1+1/((4*(9*8+1)))))) Input: 3+1/(7+1/(5*3+1/(1+1/((4*(9*8+1)))))) RPN string: 317153*111498*1+*/+/+/+/+ Value: 3.1415926530119025

    1+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2)))))))))))))))))))) Input: 1+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2+1/(2)))))))))))))))))))) RPN string: 11212121212121212121212121212121212121212/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+/+ Value: 1.414213562373095 (Note:sqrt(2) = 1.414213562373095048801688724209...)


    Revision date: 2001-10-02. (Please use ISO 8601, the International Standard.)