博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
表达式算法java实现
阅读量:6843 次
发布时间:2019-06-26

本文共 12792 字,大约阅读时间需要 42 分钟。

hot3.png

package bd;import java.util.Scanner;import java.util.Stack;public class Calculator {        public static final String USAGE = "== usage ==\n"              + "input the expressions, and then the program "              + "will calculate them and show the result.\n"              + "input 'bye' to exit.\n";        /**        * @param args        */        public static void main(String[] args) {      	      	  String input = "(+ (- 12 2) (* 4 5))";     	  toPolishNotation(input);      	  //toReversePolishNotation(input);      	             /* System.out.println(USAGE);              Scanner scanner = new Scanner(System.in);              String input = "";              final String CLOSE_MARK = "bye";              System.out.println("input an expression:");              input = scanner.nextLine();              while (input.length() != 0                    && !CLOSE_MARK.equals((input))) {                    System.out.print("Polish Notation (PN):");                    try {                          toPolishNotation(input);                    } catch (NumberFormatException e) {                          System.out.println("\ninput error, not a number.");                    } catch (IllegalArgumentException e) {                          System.out.println("\ninput error:" + e.getMessage());                    } catch (Exception e) {                          System.out.println("\ninput error, invalid expression.");                    }                    System.out.print("Reverse Polish Notation (RPN):");                    try {                          toReversePolishNotation(input);                    } catch (NumberFormatException e) {                          System.out.println("\ninput error, not a number.");                    } catch (IllegalArgumentException e) {                          System.out.println("\ninput error:" + e.getMessage());                    } catch (Exception e) {                          System.out.println("\ninput error, invalid expression.");                    }                    System.out.println("input a new expression:");                    input = scanner.nextLine();              }  */            System.out.println("program exits");        }        /**        * parse the expression , and calculate it.        * @param input        * @throws IllegalArgumentException        * @throws NumberFormatException        */        private static void toPolishNotation(String input)                    throws IllegalArgumentException, NumberFormatException {              int len = input.length();              char c, tempChar;              Stack< Character> s1 = new Stack< Character>();              Stack< Double> s2 = new Stack< Double>();              Stack< Object> expression = new Stack< Object>();              double number;              int lastIndex = -1;              for (int i=len-1; i>=0; --i) {                    c = input.charAt(i);                    if (Character.isDigit(c)) {                          lastIndex = readDoubleReverse(input, i);                          number = Double.parseDouble(input.substring(lastIndex, i+1));                          s2.push(number);                          i = lastIndex;                          if ((int) number == number)                                expression.push((int) number);                          else                                expression.push(number);                    } else if (isOperator(c)) {                          while (!s1.isEmpty()                                      && s1.peek() != ')'                                      && priorityCompare(c, s1.peek()) < 0) {                                expression.push(s1.peek());                                s2.push(calc(s2.pop(), s2.pop(), s1.pop()));                          }                          s1.push(c);                    } else if (c == ')') {                          s1.push(c);                    } else if (c == '(') {                          while ((tempChar=s1.pop()) != ')') {                                expression.push(tempChar);                                s2.push(calc(s2.pop(), s2.pop(), tempChar));                                if (s1.isEmpty()) {                                      throw new IllegalArgumentException(                                            "bracket dosen't match, missing right bracket ')'.");                                }                          }                    } else if (c == ' ') {                          // ignore                    } else {                          throw new IllegalArgumentException(                                      "wrong character '" + c + "'");                    }              }              while (!s1.isEmpty()) {                    tempChar = s1.pop();                    expression.push(tempChar);                    s2.push(calc(s2.pop(), s2.pop(), tempChar));              }              while (!expression.isEmpty()) {                    System.out.print(expression.pop() + " ");              }              double result = s2.pop();              if (!s2.isEmpty())                    throw new IllegalArgumentException("input is a wrong expression.");              System.out.println();              if ((int) result == result)                    System.out.println("the result is " + (int) result);              else                    System.out.println("the result is " + result);        }        /**        * parse the expression, and calculate it.        * @param input        * @throws IllegalArgumentException        * @throws NumberFormatException        */        private static void toReversePolishNotation(String input)                    throws IllegalArgumentException, NumberFormatException {              int len = input.length();              char c, tempChar;              Stack< Character> s1 = new Stack< Character>();              Stack< Double> s2 = new Stack< Double>();              double number;              int lastIndex = -1;              for (int i=0; i< len; ++i) {                    c = input.charAt(i);                    if (Character.isDigit(c) || c == '.') {                          lastIndex = readDouble(input, i);                          number = Double.parseDouble(input.substring(i, lastIndex));                          s2.push(number);                          i = lastIndex - 1;                          if ((int) number == number)                                System.out.print((int) number + " ");                          else                                System.out.print(number + " ");                    } else if (isOperator(c)) {                          while (!s1.isEmpty()                                      && s1.peek() != '('                                      && priorityCompare(c, s1.peek()) <= 0) {                                System.out.print(s1.peek() + " ");                                double num1 = s2.pop();                                double num2 = s2.pop();                                s2.push(calc(num2, num1, s1.pop()));                          }                          s1.push(c);                    } else if (c == '(') {                          s1.push(c);                    } else if (c == ')') {                          while ((tempChar=s1.pop()) != '(') {                                System.out.print(tempChar + " ");                                double num1 = s2.pop();                                double num2 = s2.pop();                                s2.push(calc(num2, num1, tempChar));                                if (s1.isEmpty()) {                                      throw new IllegalArgumentException(                                            "bracket dosen't match, missing left bracket '('.");                                }                          }                    } else if (c == ' ') {                          // ignore                    } else {                          throw new IllegalArgumentException(                                      "wrong character '" + c + "'");                    }              }              while (!s1.isEmpty()) {                    tempChar = s1.pop();                    System.out.print(tempChar + " ");                    double num1 = s2.pop();                    double num2 = s2.pop();                    s2.push(calc(num2, num1, tempChar));              }              double result = s2.pop();              if (!s2.isEmpty())                    throw new IllegalArgumentException("input is a wrong expression.");              System.out.println();              if ((int) result == result)                    System.out.println("the result is " + (int) result);              else                    System.out.println("the result is " + result);        }        /**        * calculate the two number with the operation.        * @param num1        * @param num2        * @param op        * @return        * @throws IllegalArgumentException        */        private static double calc(double num1, double num2, char op)                    throws IllegalArgumentException {              switch (op) {              case '+':                    return num1 + num2;              case '-':                    return num1 - num2;              case '*':                    return num1 * num2;              case '/':                    if (num2 == 0) throw new IllegalArgumentException("divisor can't be 0.");                    return num1 / num2;              default:                    return 0; // will never catch up here              }        }        /**        * compare the two operations' priority.        * @param c        * @param peek        * @return        */        private static int priorityCompare(char op1, char op2) {              switch (op1) {              case '+': case '-':                    return (op2 == '*' || op2 == '/' ? -1 : 0);              case '*': case '/':                    return (op2 == '+' || op2 == '-' ? 1 : 0);              }              return 1;        }        /**        * read the next number (reverse)        * @param input        * @param start        * @return        * @throws IllegalArgumentException        */        private static int readDoubleReverse(String input, int start)                    throws IllegalArgumentException {              int dotIndex = -1;              char c;              for (int i=start; i>=0; --i) {                    c = input.charAt(i);                    if (c == '.') {                          if (dotIndex != -1)                                throw new IllegalArgumentException(                                      "there have more than 1 dots in the number.");                          else                                dotIndex = i;                    } else if (!Character.isDigit(c)) {                          return i + 1;                    } else if (i == 0) {                          return 0;                    }              }              throw new IllegalArgumentException("not a number.");        }                /**        * read the next number        * @param input        * @param start        * @return        * @throws IllegalArgumentException        */        private static int readDouble(String input, int start)        throws IllegalArgumentException {              int len = input.length();              int dotIndex = -1;              char c;              for (int i=start; i< len; ++i) {                    c = input.charAt(i);                    if (c == '.') {                          if (dotIndex != -1)                                throw new IllegalArgumentException(                                "there have more than 1 dots in the number.");                          else if (i == len - 1)                                throw new IllegalArgumentException(                                "not a number, dot can't be the last part of a number.");                          else                                dotIndex = i;                    } else if (!Character.isDigit(c)) {                          if (dotIndex == -1 || i - dotIndex > 1)                                return i;                          else                                throw new IllegalArgumentException(                                "not a number, dot can't be the last part of a number.");                    } else if (i == len - 1) {                          return len;                    }              }                            throw new IllegalArgumentException("not a number.");        }        /**        * return true if the character is an operator.        * @param c        * @return        */        private static boolean isOperator(char c) {              return (c=='+' || c=='-' || c=='*' || c=='/');        }  }

转载于:https://my.oschina.net/u/1388024/blog/179754

你可能感兴趣的文章
Uvaoj10054 - The Necklace
查看>>
玩转树莓派:OpenHAB的入门(二)
查看>>
.Net 中的序列化与反序列化 (转)
查看>>
linux系统管理 简单常用命令
查看>>
人工智能现在可以作画了
查看>>
重温.NET下Assembly的加载过程
查看>>
华先胜:城市大脑模仿者众多,揭秘阿里原版真正的技术实力
查看>>
使用 redis 缓存的经验
查看>>
udev安全补丁
查看>>
struts2标签常用
查看>>
http中post和get的区别
查看>>
从硬盘安装ubuntu的方法
查看>>
TCPDUMP中文手册
查看>>
apache 403 forbidden 错误解决方法
查看>>
ERP实施流程-步骤
查看>>
谈Excel的一些操作
查看>>
24.NAT地址转换技术
查看>>
mahout所实现的算法
查看>>
MFC中的CListCtrl网格控件添加行
查看>>
orzdba安装与使用
查看>>