计算器算法
oneday做了计算器的界面,网上搜了下算法,但是搜不到具体的java代码,闲来无事,写了个,欢迎大家来喷!
* @author superGenius吴大仙^^!蛋疼仔
* 计算器算法的实现
*定义两个堆栈,一个放置操作数,一个放置操作符
*1.首先把得到的数学表达式转化成为逆波兰式 Reverse Polish Notation
* 对于一个表达式,遇到数字便+入到新的逆波兰式,假如遇到的是操作符,首先比较其和操作符堆栈里面
* 操作符的优先级,假如优先级较高,便加入到操作符堆栈中,or+入到逆波兰式中
* 2.计算逆波兰式
* 遍历波兰式,遇到数字便放入堆栈,遇到操作符,操作数堆栈弹出,执行相应的操作符操作,util...then ok;
- import java.util.HashMap;
- import java.util.Map;
- import java.util.Stack;
- public class CalculatorIn {
- private Stack<Double> operandStack=new Stack<Double>();//操作数堆栈
- private Stack<String> operatorStack=new Stack<String>();//操作符堆栈
- private String expression;//算数表达式
- private double result=0.0;//计算结果
- private Map<String,Integer> priorityMap=new HashMap<String,Integer>();//用于存储操作符优先级的Map
- //初始化优先级约定(可根据计算的复杂程度扩展)
- public CalculatorIn()
- {
- priorityMap.put("+",0);
- priorityMap.put("-",0);
- priorityMap.put("*", 1);
- priorityMap.put("/", 1);
- }
- public int getPriority(String op)//得到一个操作符的优先级
- {
- return priorityMap.get(op);
- }
- public boolean highPriority(String op)//判断操作符的优先级在堆栈里面是否最为高
- {
- int opPri=getPriority(op);//当前操作符的优先级
- if(!operatorStack.empty())
- {
- for(String s:operatorStack)
- {
- int priority=getPriority(s);
- if(opPri<priority)
- return false;
- }
- }
- return true;
- }
- //把表达式转化成逆波兰式
- public String expToIpn()
- {
- int index=0;
- int end=0;
- String Ipn="";
- for(int i=0;i<expression.length();i++)
- {
- String temps=String.valueOf(expression.charAt(i));
- if(temps.matches("[0-9.]"))//检查是否是数字
- {
- end++;
- }
- else
- {
- String tempOperand=expression.substring(index,end);//得到操作数
- Ipn+=tempOperand+",";
- String tempOperator=expression.substring(end,++end);//得到操作符
- if(tempOperator.equals("!"))//假如到表达式的最后将操作符 全部弹出
- {
- while(!operatorStack.empty())
- {
- Ipn+=operatorStack.pop()+",";
- }
- }
- else
- {
- if(highPriority(tempOperator))//优先级高的压入操作符堆栈
- {
- operatorStack.push(tempOperator);
- }
- else
- {
- while(!operatorStack.empty())//
- {
- Ipn+=operatorStack.pop()+",";
- }
- operatorStack.push(tempOperator);
- }
- //System.out.println(tempOperand+","+tempOperator);
- index=end;
- }
- }
- }
- return Ipn;
- }
- public double calculateIpn(String[] Ipn)//计算逆波兰式
- {
- for(int i=0;i<Ipn.length;i++)
- {
- // System.out.println(Ipn[i]);
- if(Ipn[i].matches("^[0-9]+.?[0-9]*$"))//正则表达式判断是数字
- {
- operandStack.push(Double.parseDouble(Ipn[i]));
- }
- else
- {
- popOperand(Ipn[i]);
- }
- }
- return result;
- }
- //遇到操作符时,弹出操作数,进行相应操作,并保村result
- public void popOperand(String operator)
- {
- double d1=operandStack.pop();
- double d2=operandStack.pop();
- System.out.println(d1+operator+d2);
- if(operator.equals("+"))
- result=d2+d1;
- if(operator.equals("-"))
- result=d2-d1;
- if(operator.equals("*"))
- result=d2*d1;
- if(operator.equals("/"))
- result=d2/d1;
- //System.out.println(result);
- operandStack.push(result);
- }
- public Stack getOperandStack() {
- return operandStack;
- }
- public void setOperandStack(Stack operandStack) {
- this.operandStack = operandStack;
- }
- public Stack getOperatorStack() {
- return operatorStack;
- }
- public void setOperatorStack(Stack operatorStack) {
- this.operatorStack = operatorStack;
- }
- public String getexpression_r() {
- return expression;
- }
- public void setexpression_r(String expression) {
- this.expression = expression;
- }
- public double getResult() {
- return result;
- }
- public void setResult(double result) {
- this.result = result;
- }
- public static void main(String[] args)
- {
- CalculatorIn cal=new CalculatorIn();
- String exp="32+1*2*2/2*2-2/2!";
- cal.setexpression_r(exp);
- String[] Ipn=cal.expToIpn().split(",");
- for(int i=0;i<Ipn.length;i++)
- System.out.println(Ipn[i]);
- System.out.println(cal.calculateIpn(Ipn));
- }
posted on 2011-09-07 21:39 RorySmart 阅读(7008) 评论(2) 编辑 收藏 举报