6

I need to implement function public int eval(String infix) {...} and when I use this like this:

eval("3+2*(4+5)") 

I must receive 21.

The arithmetic expression can contain '+', '*' and parentheses.

So, how can I convert this to math equation? I can't use non-standard libs.

UPDATE: Solution found.

It is 2 way: Polish Notation and using ScriptEngine.


Peter O.
  • 32,158
  • 14
  • 82
  • 96
JohnDow
  • 1,242
  • 4
  • 22
  • 40
  • 5
    What did you try so far? – Maroun Dec 01 '12 at 17:49
  • hint: [BODMAS](http://en.wikipedia.org/wiki/Order_of_operations), [stack](http://docs.oracle.com/javase/6/docs/api/java/util/Stack.html). – Prasanth Dec 01 '12 at 17:51
  • Do you have to implement basic mechanism or can u use something like ScriptEngine (available since Java 1.6)? [Example](http://stackoverflow.com/a/13407680/1393766) – Pshemo Dec 01 '12 at 17:58
  • you can use this algorithm [Polish notation][1] [1]: http://stackoverflow.com/questions/13662001/java-string-to-math-equation-beginner-level?s=40a5f65b-95c3-4b71-8403-a876a709138d#new-answer – Fido Dec 01 '12 at 17:59

3 Answers3

12

Believe it or not, with JDK1.6, you can use the built-in Javascript engine. Customise to suit your needs.

Make sure you have these imports...

import javax.script.ScriptEngineManager;
import javax.script.ScriptEngine;

Code:

ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine engine = mgr.getEngineByName("JavaScript");
String infix = "3+2*(4+5)";
System.out.println(engine.eval(infix));
xagyg
  • 9,562
  • 2
  • 32
  • 29
  • What are the various engines name available other than javascript? – vikiiii Dec 03 '12 at 05:32
  • @vikiiii Just Javascript - http://www.java2s.com/Code/JavaAPI/javax.script/ScriptEngineFactorygetEngineName.htm - Output - Mozilla Rhino, 1.7 release 3 PRERELEASE, ECMAScript, 1.8, [js], [application/javascript, application/ecmascript, text/javascript, text/ecmascript],[js, rhino, JavaScript, javascript, ECMAScript, ecmascript] – xagyg Dec 03 '12 at 23:56
3

Well first off, you'd want to tokenize the string. Essentially, separate each element. Separate the operations from the individual numbers, and store them in something (maybe a list). Then just go through the operations based upon the order of operations.

So the pseudocode would be something like:

public int eval(String infix)
{
    create a list of all the elements
    identify which operations you would want to do first
    perform the operations and simplify the list (e.g. if 5x4 were inside parantheses, remove the parantheses and replace it overall with 20.)
    continue the simplification until you have a final result
    return the result
}

There are probably much better ways to do this, but here's one solution.

Clark
  • 1,357
  • 1
  • 7
  • 18
1
  static int eval(String infix) {        
        ScriptEngineManager mgr = new ScriptEngineManager();
        ScriptEngine engine = mgr.getEngineByName("JavaScript");    
        String stringResult;
        try {
            stringResult = engine.eval(infix).toString();
            double doubleResult = Double.parseDouble(stringResult);
            int result = (int) doubleResult;        
            return result;
        } catch (ScriptException ex) {
            Logger.getLogger(Ukol4a.class.getName()).log(Level.SEVERE, null, ex);
        }
        return(1);

    }
JohnDow
  • 1,242
  • 4
  • 22
  • 40