加减乘除运算(Java)

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了加减乘除运算(Java)相关的知识,希望对你有一定的参考价值。

需要输入一串字符串,(当然都是数字和运算符号)
然后得出结果
麻烦了
需要输入的是比如: 83-32+83*32/4+3
然后直接得出答案。

实际上这相当于javascript的eval方法,以下是该方法的java实现:

//Eval.java
import java.util.ArrayList;
import java.util.List;
import java.util.Stack;

public class Eval
public int eval(String exp)
List<String> list = infixExpToPostExp(exp);//转化成后缀表达式
return doEval(list);//真正求值


//遇到操作符压栈,遇到表达式从后缀表达式中弹出两个数,计算出结果,压入堆栈
private int doEval(List<String> list)
Stack<String> stack = new Stack<String>();
String element;
int n1,n2,result;
try
for(int i = 0; i < list.size();i++)
element = list.get(i);
if(isOperator(element))
n1 = Integer.parseInt(stack.pop());
n2 = Integer.parseInt(stack.pop());
result = doOperate(n1,n2,element);
stack.push(new Integer(result).toString());
else
stack.push(element);


return Integer.parseInt(stack.pop());
catch(RuntimeException e)
throw new IllegalExpressionException(e.getMessage());



private int doOperate(int n1, int n2, String operator)
if(operator.equals("+"))
return n1 + n2;
else if(operator.equals("-"))
return n1 - n2;
else if(operator.equals("*"))
return n1 * n2;
else
return n1 / n2;


private boolean isOperator(String str)
return str.equals("+") || str.equals("-") || str.equals("*") || str.equals("/");


private List<String> infixExpToPostExp(String exp)//将中缀表达式转化成为后缀表达式
List<String> postExp = new ArrayList<String>();//存放转化的后缀表达式的链表
StringBuffer numBuffer = new StringBuffer();//用来保存一个数的
Stack<Character> opStack = new Stack<Character>();//操作符栈
char ch,preChar;
opStack.push('#');
try
for(int i = 0; i < exp.length();)
ch = exp.charAt(i);
switch(ch)
case '+':
case '-':
case '*':
case '/':
preChar = opStack.peek();
// 如果栈里面的操作符优先级比当前的大,则把栈中优先级大的都添加到后缀表达式列表中
while(priority(preChar) >= priority(ch))
postExp.add(""+preChar);
opStack.pop();
preChar = opStack.peek();

opStack.push(ch);
i++;
break;
case '(':
// 左括号直接压栈
opStack.push(ch);
i++;
break;
case ')':
// 右括号则直接把栈中左括号前面的弹出,并加入后缀表达式链表中
char c = opStack.pop();
while(c != '(')
postExp.add("" + c);
c = opStack.pop();

i++;
break;
// #号,代表表达式结束,可以直接把操作符栈中剩余的操作符全部弹出,并加入后缀表达式链表中
case '#':
char c1;
while(!opStack.isEmpty())
c1 = opStack.pop();
if(c1 != '#')
postExp.add("" + c1);

i++;
break;
//过滤空白符
case ' ':
case '\t':
i++;
break;
// 数字则凑成一个整数,加入后缀表达式链表中
default:
if(Character.isDigit(ch))
while(Character.isDigit(ch))
numBuffer.append(ch);
ch = exp.charAt(++i);

postExp.add(numBuffer.toString());
numBuffer = new StringBuffer();
else
throw new IllegalExpressionException("illegal operator");



catch(RuntimeException e)
throw new IllegalExpressionException(e.getMessage());

return postExp;


private int priority(char op)//定义优先级
switch(op)
case'+':
case'-':
return 1;
case'*':
case'/':
return 2;
case'(':
case'#':
return 0;

throw new IllegalExpressionException("Illegal operator");




Main.java 主函数所在类
public class Main

public static void main(String[] args)

try
InputStreamReader isr=new InputStreamReader(System.in);
BufferedReader br=new BufferedReader(isr);
String exp=br.readLine();

int result = eval.eval(exp);
System.out.println(result);

catch (IOException e)
// TODO Auto-generated catch block
e.printStackTrace();





IllegalExpressionException异常类
public class IllegalExpressionException extends RuntimeException

public IllegalExpressionException()



public IllegalExpressionException(String info)
super(info);

参考技术A

//MathX.java

//表达式计算程序,绝对原创,

//与网上多数介绍的方法思路有点不同,

//与采用直接调用js的方法有根本的不同,

//支持 加 减 乘 除 幂 及 开方 运算,支持多级括号,

//本程序在 JDK1.6_11下开发,低版本JDK兼容性未测试,

import java.text.DecimalFormat;

public class MathX 

 public static void main(String[] args) 

  String str = "83-32+83*32/4+3";

  double d = Calc.doCalc(str).getValue();

  System.out.println(Calc.getStr()+"="+d);

 

// public static double calc(String s)

//  return Calc.doCalc(s).getValue();

// 

// public static String getStr()

//  return Calc.getStr();

// 

// public static String getFormatted() 

//  return Calc.getFormatted();

// 

class Calc

 private static final DecimalFormat df = new DecimalFormat("0.000000");

 private static CalcCore co;

 private static NumberWrapper result;

 public static NumberWrapper doCalc(String exp)

  co = new CalcCore(exp);

  result = co.getResult();

  return result;

 

 public static String getFormatted() 

  return df.format(result.getValue());

 

 public static String getStr()return co.toString();

//数据外覆类

class NumberWrapper

 public static final int IaN = 0;

 public static final int NaN = 1;

 public static final NumberWrapper NOTHING = new NumberWrapper(Double.NaN,NumberWrapper.NaN);

 private double value;

 private int id;

 

 public NumberWrapper(double v)

  this(v,NumberWrapper.IaN);

 

 public double getValue()

  return id==NumberWrapper.IaN?value:Double.NaN;

 

 public NumberWrapper(double v,int id)

  this.value=v;

  this.id=id;

 

 // +-*/^~

 public NumberWrapper calc(NumberWrapper x,char o)

  if(this.NaN()||x.NaN())

   return NumberWrapper.NOTHING;

  return new NumberWrapper(calc(this.getValue(),x.getValue(),o));

 

 private double calc(double a,double b,char o)

  try

   switch(o)

   case OStack.PLUS:return a+b;

   case OStack.SUBTRACT:return a-b;

   case OStack.MULTIPLY:return a*b;

   case OStack.DIVIDE:return a/b;

   case OStack.POWER:return Math.pow(a, b);

   case OStack.EVOLUTION:return Math.pow(a, 1d/b);

   default:return Double.NaN;

   

  catch(Exception e)

  return Double.NaN;

 

 

 public void setId(int id)this.id=id;

 public boolean NaN()return id==NaN;

class CalcCore

 private NStack n;

 private OStack o;

 private NumberWrapper result;

 private String src;

 

 public CalcCore(String src)

  this.src=src;

  rebuildString();

  this.n=new NStack();

  this.o=new OStack();

  this.split();

  this.calc();

 

 public String toString()

  return src;

 

 private void rebuildString() 

  // (...)(...) --> (...)*(...)

  src=src.replaceAll("\\\\)\\\\(",")"+OStack.MULTIPLY+"(");

  // 1234(...) --> 1234*(...)

  // (...)1234 --> (...)*1234

  int i=0;

  while(i<src.length())

   if(hasNext(i+1)&&this.isNumber(i)&&src.charAt(i+1)==OStack.LB||

     hasNext(i+1)&&this.isNumber(i+1)&&src.charAt(i)==OStack.RB)

    src=src.substring(0,i+1)+OStack.MULTIPLY+src.substring(i+1);

   

   ++i;

  

  //~1234 -->2~1234

  //(~1234) -->(2~1234)

  i=0;

  while(i<src.length())

   if(src.charAt(i)==OStack.EVOLUTION && pio(i))

    src=src.substring(0,i)+"2"+src.substring(i);

   

   ++i;

  

 

 private void calc() 

  for(int i=0; i<o.size(); i++)

   char ch = o.get(i);

   if(ch==OStack.EVOLUTION||ch==OStack.POWER)

    NumberWrapper n0 = n.remove(i);

    NumberWrapper n1 = n.remove(i);

    ch = o.remove(i);

    NumberWrapper rs;

    if(ch==OStack.EVOLUTION)

     rs = n0.calc(n1, ch);

    else

     rs = n1.calc(n0, ch);

    n.insert(i, rs);

    --i;

   

  

  for(int i=o.size()-1; i>=0; i--)

   char ch = o.get(i);

   if(ch==OStack.MULTIPLY||ch==OStack.DIVIDE)

    NumberWrapper n0 = n.remove(i+1);

    NumberWrapper n1 = n.remove(i);

    ch = o.remove(i);

    NumberWrapper rs = n0.calc(n1, ch);

    n.insert(i, rs);

   

  

  for(int i=o.size()-1; i>=0; i--)

   char ch = o.get(i);

   NumberWrapper n0 = n.remove(i+1);

   NumberWrapper n1 = n.remove(i);

   ch = o.remove(i);

   NumberWrapper rs = n0.calc(n1, ch);

   n.insert(i, rs);

  

  if(n.isEmpty()||n.size()>1)

   result = NumberWrapper.NOTHING;

  else

   result = n.pop();

 

 public NumberWrapper getResult()

  return result;

 

 private void split()

  int cont;

  for(int i=0; i<src.length(); i++)

   char c = src.charAt(i);

   switch(c)

   case '(':

    int pair = nextPair(src,i+1);

    String sub = substring(i+1,pair);

    n.push(Calc.doCalc(sub));

    i=pair;

    break;

   case '-':

   case '+':

    boolean iso = pio(i);

    cont = continuous(i+1);

    if(iso)

     n.push(new NumberWrapper(parse(substring(i,cont))));

     i=cont-1;

     break;

    

   case '*':

   case '/':

   case '%':

   case '^':

   case '~':o.push(c);break;

   default :

    cont = continuous(i+1);

    n.push(new NumberWrapper(parse(substring(i,cont))));

    i=cont-1;

   

  

 

 private double parse(String s)

  try

   return Double.parseDouble(s);

  catch(Exception e)

  return Double.NaN;

 

 private String substring(int i, int cont) 

  return src.substring(i,cont);

 

 private boolean hasNext(int i)

  return src.length()>i;

 

 private int continuous(int i) 

  while(hasNext(i) && isNumber(i))

    ++i;

  return i;

 

 private boolean pio(int i)

  return i<1?true:OStack.iso(src.charAt(i-1));

 

 public boolean isNumber(int pos)

  char c = src.charAt(pos);

  return c<='9' && c>='0' || c=='.';

 

 public int nextPair(String src,int pos)

  int inner = 0;

  int len = src.length();

  for(int i=pos; i<len; i++)

   char c = src.charAt(i);

   if(c==')')

    if(inner==0)return i;

    else --inner;

   else if(c=='(')++inner;

  

  return -1;

 

//操作符栈(半角符号)

class OStack

 public static final char PLUS = '+';

 public static final char SUBTRACT = '-';

 public static final char MULTIPLY = '*';

 public static final char DIVIDE = '/';

 public static final char POWER = '^';

 public static final char EVOLUTION = '~';

 public static final char LB = '(';

 public static final char RB = ')';

 public static boolean iso(char c) 

  switch(c)

  case PLUS:

  case SUBTRACT:

  case MULTIPLY:

  case DIVIDE:

  case POWER:

  case EVOLUTION:

  case LB:

//  case RB:

   return true;

  

  return false;

 

 

 public boolean hasNext(int i) 

  return this.length>i+1;

 

 private char[] stack;

 private int length;

 

 public OStack()

  this.stack=new char[0];

  this.length=0;

 

 public boolean isEmpty()

  return length==0;

 

 public void push(char c)

  char[] tmp = new char[this.length+1];

  tmp[0]=c;

  System.arraycopy(stack, 0, tmp, 1, length);

  ++length;

  this.stack=tmp;

 

 public char pop()

  if(this.isEmpty())throw new StackOverflowError();

  char c = stack[0];

  char[] tmp = new char[length-1];

  System.arraycopy(stack, 1, tmp, 0, tmp.length);

  --length;

  this.stack=tmp;

  return c;

 

 public char remove(int i)

  if(i<0||i>=length)throw new StackOverflowError();

  char[] tmp = new char[length-1];

  System.arraycopy(stack,0,tmp,0,i);

  System.arraycopy(stack,i+1,tmp,i,tmp.length-i);

  this.length--;

  char n=stack[i];

  this.stack=tmp;

  return n;

 

 public void insert(int i,char n)

  if(i<0||i>length)throw new StackOverflowError();

  char[] tmp = new char[length+1];

  System.arraycopy(stack,0,tmp,0,i);

  System.arraycopy(stack,i,tmp,i+1,this.length-i);

  tmp[i]=n;

  this.length++;

  this.stack=tmp;

 

 public char get(int i)

  return this.stack[i];

 

 public int size()return this.length;

//数据栈

class NStack

 private NumberWrapper[] stack;

 private int length;

 public NStack()

  this.stack=new NumberWrapper[0];

  this.length=0;

 

 public NStack(NStack n)

  this.stack=new NumberWrapper[n.length];

  this.length=n.length;

  for(int i=0; i<length; i++)

   this.stack[i]=n.stack[i];

  

 

 public void push(NumberWrapper d)

  NumberWrapper[] tmp = new NumberWrapper[this.length+1];

  System.arraycopy(stack, 0, tmp, 1, this.length);

  tmp[0] = d;

  this.stack=tmp;

  this.length++;

 

 public NumberWrapper pop() throws StackOverflowError

  if(this.isEmpty())throw new StackOverflowError();

  NumberWrapper[] tmp = new NumberWrapper[this.length-1];

  System.arraycopy(stack, 1, tmp, 0, tmp.length);

  NumberWrapper d = stack[0];

  this.stack=tmp;

  this.length--;

  return d;

 

 public NumberWrapper get(int i)

  return this.stack[i];

 

 public NumberWrapper remove(int i)

  if(i<0||i>=length)throw new StackOverflowError();

  NumberWrapper[] tmp = new NumberWrapper[length-1];

  System.arraycopy(stack,0,tmp,0,i);

  System.arraycopy(stack,i+1,tmp,i,tmp.length-i);

  this.length--;

  NumberWrapper n=stack[i];

  this.stack=tmp;

  return n;

 

 public void insert(int i,NumberWrapper n)

  if(i<0||i>length)throw new StackOverflowError();

  NumberWrapper[] tmp = new NumberWrapper[length+1];

  System.arraycopy(stack,0,tmp,0,i);

  System.arraycopy(stack,i,tmp,i+1,this.length-i);

  tmp[i]=n;

  this.length++;

  this.stack=tmp;

 

 public boolean isEmpty()

  return this.length==0;

 

 public int size()return this.length;

本回答被提问者采纳
参考技术B 大体就跟 fantasy316 写的大同小异,使用堆栈做。一个一个字符读,操作符入栈,操作数直接写出,然后根据运算优先级写出符号,建立后缀表达式;再根据后缀表达式利用栈结构算出最后结果。 参考技术C 应该是JS的吧 不与WEB交互计算的话估计取值有点麻烦

因为不能判断你的值是多少位 运算符号在什么地方

当然了要真不是WEB的截面的话 可以把输入的转化成ASCII进行比较
分解出是值还是运算符 然后进行操作

不过这个判断是有的写了
参考技术D class test3

public static void main(String[] args)throws Exception

try
System.out.println(myMath("(12+15)*56+45681"));
catch(javax.script.ScriptException se)



public static double myMath(String s) throws javax.script.ScriptException
Object o = new javax.script.ScriptEngineManager().getEngineByName("JavaScript").eval(s);
return (Double)o;

以上是关于加减乘除运算(Java)的主要内容,如果未能解决你的问题,请参考以下文章

JAVA中哪些基本数据类型支持加减乘除四则运算

java中怎么将字符串(带运算符号加减乘除)转换成代数算式运算

java用位运算实现加减乘除

java BigDecimal实现精确加减乘除运算

“VS”编写“加减乘除”运算的代码?

简单的java程序通过对话框输出 计算加减乘除运算(运算方法可选择)