【數據結構】利用棧來求算術表達式的值

前提是:算術表達式是完全帶括號的數字表達式


import java.util.Scanner;
import java.util.Stack;
import java.util.regex.Pattern;


public class CalculateUtils
{
public static final Pattern UNSIGNED_DOUBLE = 
Pattern.compile("((\\d+\\.?\\d*)|(\\.\\d+))([Ee][-+]?\\d+)?.*?");
public static final Pattern CHARACTER = 
Pattern.compile("\\S.*?");
/**
* 對算法表達式求值
* @param expression 一個完全括號化了的算術表達式
* @return 算術表達式的值
*/
public static double evaluate(String expression)
{
// 使用兩個棧來分別保存表達式中的數值和運算符
Stack<Double> numbers = new Stack<Double>();
Stack<Character> operations = new Stack<Character>();

// 將表達式轉換成一個Scanner類的對象,以便更易於處理
Scanner input = new Scanner(expression);
// next存儲的是表達式的下一個片段:數值、運算符或括號
String next;

while (input.hasNext())
{
if (input.hasNext(UNSIGNED_DOUBLE))
{
next = input.findInLine(UNSIGNED_DOUBLE);
numbers.push(new Double(next));
} else {
next = input.findInLine(CHARACTER);
switch (next.charAt(0))
{
case '+':
case '-':
case '*':
case '/':
operations.push(next.charAt(0));
break;
case ')':
evaluateStackTops(numbers, operations);
break;
case '(':
break;
default:
throw new IllegalArgumentException("Illegal input expression.");
}
}
}
if (numbers.size() != 1)
{
throw new IllegalArgumentException("Illegal input expression.");
}
return numbers.pop();
}

/**
* 從數值棧中取出兩個數值,並執行一次運算
* @param numbers
* @param operations
*/
public static void evaluateStackTops(Stack<Double> numbers, Stack<Character> operations)
{
double operand1, operand2;
if ((numbers.size() < 2) || (operations.isEmpty()))
{
throw new IllegalArgumentException("Illegal expression.");
}

operand2 = numbers.pop();
operand1 = numbers.pop();

switch (operations.pop())
{
case '+':
numbers.push(operand1 + operand2);
break;
case '-':
numbers.push(operand1 - operand2);
break;
case '*':
numbers.push(operand1 * operand2);
break;
case '/':
numbers.push(operand1 / operand2);
break;
default:
throw new IllegalArgumentException("Illegal operation.");
}
}

public static void main(String[] args)
{
String s1 = "((((12+9)/3)+7.2)*((6-4)/8))";
double value1 = CalculateUtils.evaluate(s1);
System.out.println(value1);

String s2 = "((((6+9)/3)*(6-4))";
double value2 = CalculateUtils.evaluate(s2);
System.out.println(value2);
}
}
計算結果:
3.55
10.0


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章