中綴表達式轉換為后綴表達式


中綴表達式轉換成后綴表達式

  1、概述

    可以看到,后綴表達式適合計算式進行運算,但是人卻不太容易寫出來,尤其是表達式很長得情況下,因此在開發中,需要將 中綴表達式轉成后綴表達式

  2、具體步驟

1.初始化兩個棧:運算符棧s1和儲存中間結果的棧s2;
2.從左至右掃描中綴表達式;
3.遇到操作數時,將其壓s2;
4.遇到運算符時,比較其與s1棧頂運算符的優先級:
 (1)如果s1為空,或棧頂運算符為左括號“(”,則直接將此運算符入棧;
 (2)否則,若優先級比棧頂運算符的高,也將運算符壓入s1;
 (3)否則,將s1棧頂的運算符彈出並壓入到s2中,再次轉到(4.1)與s1中新的棧頂運算符相比較;	
5.遇到括號時:
 (1)如果是左括號"(",則直接壓入s1
 (2)如果是右括號")",則依次彈出s1棧頂的運算符,並壓入s2,直到遇到左括號為止,此時將這一對括號丟棄
6.重復步驟2至5,直到表達式的最右邊 7.將s1中剩余的運算符依次彈出並壓入s2 8.依次彈出s2中的元素並輸出,結果的逆序即為中綴表達式對應的后綴表達式

  

  3、案例

    將中綴表達式 "1+((2+3)*4)-5" 轉換為后綴表達式的過程如下:

    結果為:"1 2 3 + 4 * 5 - "

    

 

  4、思路分析示意圖

 

  5、代碼實現

 1 import java.util.ArrayList;  2 import java.util.List;  3 import java.util.Stack;  4 
 5 /**
 6  * 把中綴表達式轉成后綴表達式  7  *  8  */
 9 public class ToSuffixExpression {  10 
 11     public static void main(String[] args) {  12         // 完成一個中綴表達式轉成 后綴表達式  13         // 說明  14         // 1. 1+((2+3)*4)-5 => 轉成 123 + 4 * + 5-  15         // 2. 因為對 str進行操作不方便,先將 中綴表達式 存入 list  16         // 3.將得到的中綴表達式對應的 list轉成 =>后綴表達式對應的list  17         // 即[1,+,(,(,2,+,3,),*,4,),-,5] => [1,2,3,+,4,*,+,5,-]
 18 
 19         String expression = "1+((2+3)*4)-5";  20         List<String> list = toInfixExpressionList(expression);  21         System.out.println("中綴表達式對應的list="+list);  22         List<String> list2 = parseSuffixExpressionList(list);  23         System.out.println("后綴表達式對應的list="+list2);  24  }  25     
 26     //方法:將得到的中綴表達式對應的 list轉成 =>后綴表達式對應的list
 27     public static List<String> parseSuffixExpressionList(List<String> ls) {  28         //定義兩個棧
 29         Stack<String> s1 = new Stack<String>();  // 符號棧  30         
 31         //說明:因為 s2這個棧,在整個轉換過程中,沒有pop操作,后面還需要逆序輸出  32         //所以,把 s2 這個棧換成 List<String> 即可  33         //Stack<String> s2 = new Stack<String>(); // 存儲中間結果的棧
 34         List<String> s2 = new ArrayList<String>();  //存儲中間結果的list  35         
 36         //遍歷 ls
 37         for(String item : ls) {  38             //如果是一個棧,就加入到s2
 39             if(item.matches("\\d+")) {  40  s2.add(item);  41             } else if (item.equals("(")) {  42  s1.push(item);  43             } else if (item.equals(")")) {  44                 // 如果是右括號,則依次彈出s1棧頂的運算符,並壓入 s2,知道遇到左括號為止,此時將這一對括號丟棄
 45                 
 46                 while(!s1.peek().equals("(")) {  47  s2.add(s1.pop());  48  }  49                 s1.pop();  // 將左括號 彈出,消除小括號
 50             } else {  51                 // 當 item 的優先級小於或等於棧頂運算符,將s1棧頂的運算符彈出並壓入s2中,再次轉到4.1與s1中新的棧頂運算符相比較  52                 //問題:缺少比較優先級高低的方法
 53                 while(s1.size() != 0 && Operation.getValue(s1.peek()) >= Operation.getValue(item)) {  54  s2.add(s1.pop());  55  }  56                 //還需要將 item 壓入 棧中
 57  s1.push(item);  58  }  59  }  60         
 61         //將s1中剩余的運算符依次彈出加入s2
 62         while(s1.size()!=0) {  63  s2.add(s1.pop());  64  }  65         
 66         return s2;  //因為存放到list中,因此,按順序輸出就是對應的后綴表達式對應的 list
 67  }  68     
 69 
 70     // 方法:將中綴表達式轉成對應的 list
 71     public static List<String> toInfixExpressionList(String s) {  72         // 定義一個 list,存放中綴表達式 對應的內容
 73         List<String> ls = new ArrayList<String>();  74         int i = 0; // 指針,用於遍歷中綴表達式字符串
 75         String str; // 做對多位數的拼接工作
 76         char c; // 每遍歷到一個字符,就放入到 c
 77 
 78         do {  79             // 如果c是一個非數字,就需要加入到 ls
 80             if ((c = s.charAt(i)) < 48 || (c = s.charAt(i)) > 57) {  81                 ls.add("" + c);  82                 i++; // i后移
 83             } else { // 如果是數字,考慮多位數問題
 84                 str = ""; // 將 str置空
 85                 while (i < s.length() && (c = s.charAt(i)) >= 48 && (c = s.charAt(i)) <= 57) {  86                     str += c; // 拼接
 87                     i++;  88  }  89  ls.add(str);  90  }  91 
 92         } while (i < s.length());  93         return ls; // 返回
 94  }  95 }  96 
 97 /**
 98  * 可以返回一個運算符的對應的優先級  99  * 100  */
101 public class Operation { 102     private static int ADD = 1; 103     private static int SUB = 1; 104     private static int MUL = 2; 105     private static int DIV = 2; 106     
107     // 寫一個方法,返回對應的優先級數字
108     public static int getValue(String operation) { 109         int result = 0; 110         switch(operation) { 111         case "+": 112             result = ADD; 113             break; 114         case "-": 115             result = SUB; 116             break; 117         case "*": 118             result = MUL; 119             break; 120         case "/": 121             result = DIV; 122             break; 123         default: 124             System.out.println("不存在該運算符"); 125             break; 126  } 127         return result; 128  } 129 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM