Requirements You will be provided with an almost complete version of the Evaluat
ID: 3903875 • Letter: R
Question
Requirements
You will be provided with an almost complete version of the Evaluator class (Evaluator.java). You should program the utility classes it uses - Operand and Operator - and then follow the suggestions in the code to complete the implementation of the Evaluator class. The Evaluator implements a single public method, eval, that takes a single String parameter that represents an infix mathematical expression, parses and evaluates the expression, and returns the integer result. An example expression is 2 + 3 * 4, which would be evaluated to 14.
The expressions are composed of integer operands and operators drawn from the set +, -, *, /, ^, (, and ). These operators have the following precedence (# and ! will be discussed shortly, and they are extra credit). Operator
Priority
+, -
1
*, /
2
^
3
*********************************EVALUATOR.JAVA****************************************
import java.util.*;
public class Evaluator {
private Stack operandStack;
private Stack operatorStack;
private StringTokenizer tokenizer;
private static final String DELIMITERS = "+-*^/ ";
public Evaluator() {
operandStack = new Stack<>();
operatorStack = new Stack<>();
}
public int eval( String expression ) {
String token;
// The 3rd argument is true to indicate that the delimiters should be used
// as tokens, too. But, we'll need to remember to filter out spaces.
this.tokenizer = new StringTokenizer( expression, DELIMITERS, true );
// initialize operator stack - necessary with operator priority schema
// the priority of any operator in the operator stack other than
// the usual mathematical operators - "+-*/" - should be less than the priority
// of the usual operators
while ( this.tokenizer.hasMoreTokens() ) {
// filter out spaces
if ( !( token = this.tokenizer.nextToken() ).equals( " " )) {
// check if token is an operand
if ( Operand.check( token )) {
operandStack.push( new Operand( token ));
} else {
if ( ! Operator.check( token )) {
System.out.println( "*****invalid token******" );
System.exit( 1 );
}
// ( The Operator class should contain an instance of a HashMap,
// and values will be instances of the Operators. See Operator class
// skeleton for an example. )
Operator newOperator = new Operator( token );
while ( operatorStack.peek().priority() >= newOperator.priority() ) {
// note that when we eval the expression 1 - 2 we will
// push the 1 then the 2 and then do the subtraction operation
// This means that the first number to be popped is the
// second operand, not the first operand - see the following code
Operator oldOpr = operatorStack.pop();
Operand op2 = operandStack.pop();
Operand op1 = operandStack.pop();
operandStack.push( oldOpr.execute( op1, op2 ));
}
operatorStack.push( newOperator );
}
}
}
// Control gets here when we've picked up all of the tokens; you must add
// code to complete the evaluation - consider how the code given here
// will evaluate the expression 1+2*3
// When we have no more tokens to scan, the operand stack will contain 1 2
// and the operator stack will have + * with 2 and * on the top;
// In order to complete the evaluation we must empty the stacks (except
// the init operator on the operator stack); that is, we should keep
// evaluating the operator stack until it only contains the init operator;
// Suggestion: create a method that takes an operator as argument and
// then executes the while loop; also, move the stacks out of the main
// method
return 0;
}
}
*********************************OPERAND.JAVA****************************************
public class Operand {
public Operand( String token ) {
}
public Operand( int value ) {
}
public int getValue() {
}
public static boolean check( String token ) {
}
}
*********************************OPERATOR.JAVA****************************************
public abstract class Operator {
// The Operator class should contain an instance of a HashMap
// This map will use keys as the tokens we're interested in,
// and values will be instances of the Operators.
public abstract int priority();
public abstract Operand execute( Operand op1, Operand op2 );
public static boolean check( String token ) {
}
}
The expressions are composed of integer operands and operators drawn from the set +, -, *, /, ^, (, and ). These operators have the following precedence (# and ! will be discussed shortly, and they are extra credit). Operator
Priority
+, -
1
*, /
2
^
3
Explanation / Answer
Below is your complete code. I have added some additional code .I hope its fine. Please do rate this answer positive, If i was able to help you. Let me know if you have any issues in comments
Evaluator.java
public class Evaluator {
private Stack<Operand> operandStack;
private Stack<Operator> operatorStack;
private StringTokenizer tokenizer;
private static final String DELIMITERS = "+-*^/ ";
public Evaluator() {
operandStack = new Stack<>();
operatorStack = new Stack<>();
}
public int eval(String expression) {
operandStack.clear();
operatorStack.clear();
String token;
expression = expression + " !";
operatorStack.push(new PoundOperator());
// The 3rd argument is true to indicate that the delimiters should be
// used
// as tokens, too. But, we'll need to remember to filter out spaces.
this.tokenizer = new StringTokenizer(expression, DELIMITERS, true);
// initialize operator stack - necessary with operator priority schema
// the priority of any operator in the operator stack other than
// the usual mathematical operators - "+-*/" - should be less than the
// priority
// of the usual operators
while (this.tokenizer.hasMoreTokens()) {
// filter out spaces
if (!(token = this.tokenizer.nextToken()).equals(" ")) {
// check if token is an operand
if (Operand.check(token)) {
operandStack.push(new Operand(token));
} else {
if (!Operator.check(token)) {
System.out.println("*****invalid token******");
System.exit(1);
}
// ( The Operator class should contain an instance of a
// HashMap,
// and values will be instances of the Operators. See
// Operator class
// skeleton for an example. )
Operator newOperator = Operator.operators.get(token);
if (newOperator.priority() <= operatorStack.peek().priority()) {
while (newOperator.priority() <= operatorStack.peek().priority() && operandStack.size() > 1) {
// note that when we eval the expression 1 - 2 we
// will
// push the 1 then the 2 and then do the subtraction
// operation
// This means that the first number to be popped is
// the
// second operand, not the first operand - see the
// following code
Operator oldOpr = operatorStack.pop();
Operand op2 = operandStack.pop();
Operand op1 = operandStack.pop();
operandStack.push(oldOpr.execute(op1, op2));
}
operatorStack.push(newOperator);
} else {
operatorStack.push(newOperator);
}
}
}
}
// Control gets here when we've picked up all of the tokens; you must
// add
// code to complete the evaluation - consider how the code given here
// will evaluate the expression 1+2*3
// When we have no more tokens to scan, the operand stack will contain 1
// 2
// and the operator stack will have + * with 2 and * on the top;
// In order to complete the evaluation we must empty the stacks (except
// the init operator on the operator stack); that is, we should keep
// evaluating the operator stack until it only contains the init
// operator;
// Suggestion: create a method that takes an operator as argument and
// then executes the while loop; also, move the stacks out of the main
// method
return operandStack.peek().getValue();
}
}
Operand.java
public class Operand {
private int opdValue;
public Operand(String token) {
opdValue = Integer.parseInt(token);
}
public Operand(int value) {
opdValue = value;
}
public int getValue() {
return opdValue;
}
public static boolean check(String token) {
try {
Integer.parseInt(token);
} catch (NumberFormatException e) {
return false;
}
// only got here if we didn't return false
return true;
}
}
Operator.java
public abstract class Operator {
// The Operator class should contain an instance of a HashMap
// This map will use keys as the tokens we're interested in,
// and values will be instances of the Operators.
static HashMap<String,Operator> operators = new HashMap<>();
static {
operators.put("#", new PoundOperator());
operators.put("!", new ExclamationOperator());
operators.put("+", new AdditionOperator());
operators.put("-", new SubtractionOperator());
operators.put("*", new MultiplicationOperator());
operators.put("/", new DivisionOperator());
operators.put("^", new AndOperator());
}
public abstract int priority();
public abstract Operand execute(Operand op1, Operand op2);
public static boolean check(String token) {
return operators.containsKey(token);
}
}
class PoundOperator extends Operator {
@Override
public int priority() {
return 0;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
return null;
} // end execute
} // end PoundOperator
class ExclamationOperator extends Operator {
@Override
public int priority() {
return 1;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
return null;
} // end execute
} // end ExclamationOperator
class AdditionOperator extends Operator {
@Override
public int priority() {
return 2;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
Operand result = new Operand(opd1.getValue() + opd2.getValue());
return result;
} // end execute
} // end AdditionOperator
class SubtractionOperator extends Operator {
@Override
public int priority() {
return 2;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
Operand result = new Operand(opd2.getValue() - opd1.getValue());
return result;
} // end execute
} // end SubtractionOperator
class MultiplicationOperator extends Operator {
@Override
public int priority() {
return 3;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
Operand result = new Operand(opd1.getValue() * opd2.getValue());
return result;
} // end execute
} // end MultiplicationOperator
class DivisionOperator extends Operator {
@Override
public int priority() {
return 3;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
Operand result = new Operand(opd2.getValue() / opd1.getValue());
return result;
} // end execute
} // end DivisionOperator
class AndOperator extends Operator {
@Override
public int priority() {
return 4;
} // end priority
@Override
public Operand execute(Operand opd1, Operand opd2) {
Operand result = new Operand(opd2.getValue() ^ opd1.getValue());
return result;
} // end execute
} // end AndOperator
EvaluatorTester.java
public class EvaluatorTester {
public static void main(String[] args) {
Evaluator anEvaluator = new Evaluator();
System.out.println("2 + 3 * 4 = " + anEvaluator.eval("2 + 3 * 4"));
}
}
Output
2 + 3 * 4 = 14
Related Questions
drjack9650@gmail.com
Navigate
Integrity-first tutoring: explanations and feedback only — we do not complete graded work. Learn more.