題目描述讀入乙個只包含 +, -, *, / 的非負整數計算表示式,計算該表示式的值。
輸入測試輸入包含若干測試用例,每個測試用例佔一行,每行不超過200個字元,整數和運算子之間用乙個空格分隔。沒有非法表示式。當一行中只有0時輸入結束,相應的結果不要輸出。
輸出對每個測試用例輸出1行,即該表示式的值,精確到小數點後2位。
樣例輸入30 / 90 - 26 + 97 - 5 - 6 - 13 / 88 * 6 + 51 / 29 + 79 * 87 + 57 * 92
0
樣例輸出12178.21
解題思路:給出的是中綴表示式(即就是算數表示式中運算子總是出現在兩個運算元之間),由於電腦無法識別並且計算,所以需要轉換為字尾表示式(即就是運算子放在運算元之後),最後就是計算字尾表示式。
中綴表示式轉字尾表示式1)設立乙個操作符棧,用來臨時存放操作符;然後設立乙個陣列或者佇列,用來存放字尾表示式;
2)從左往右掃瞄中綴表示式,如果碰到運算元(注意:運算元可能不止 一位,因此需要一位一位讀入然後再合併在一起,具體實現見**),就把運算元加入到字尾表示式;
3)如果碰到操作符op,就與棧的棧頂操作符的優先順序開始比較,執行的步驟為:
若op的優先順序高於棧頂操作符優先順序,將壓入到操作符棧。
若op的優先順序低於或等於棧頂操作符優先順序,則將操作符棧的操作符不斷彈出到字尾表示式中,直到op的優先順序高於棧頂操作符的優先順序,高於之後將該操作符op壓入操作符棧。
4)重複2)到3)操作,直到中綴表示式掃瞄完畢,之後如果操作符棧中仍有元素,則將它們依次彈出到字尾表示式中。
所謂操作符的優先順序即就是它們計算的優先順序,其中乘法=除法》加法=減法。
那麼如何在**中實現 優先順序呢?,那麼可以通過映像map建立操作符和優先順序的對映,具體實現見**。
關於為什麼當op的優先順序高於棧頂時就壓入操作符棧?其實對於我來說,更好的理解方法就是按照前面的步驟進行逐步的去實現,也可以這樣自己總結:既然乘法或者除法要比加減法的優先順序 高,那肯定要在棧的最高層,進行計算字尾表示式的話也是從左往右計算,只有在棧頂,出來壓入到字尾表示式中時才可以排在最前面。
關於為什麼當op的優先順序小於或者等於的時候不能壓入操作符棧?按照操作步驟執行就可以理解。
字尾表示式計算從左往右掃瞄字尾表示式,如果是運算元,就壓入到棧,如果數操作符,就連續彈出兩個運算元(注意:後彈出的是第乙個運算元,先彈出的是蝶兒個運算元)
進行操作符的運算之後得到的結果繼續壓入到棧
執行以上兩個步驟,直到字尾表示式掃瞄完畢,這時棧中只剩下乙個數,就是最終的答案。
舉例來實現以上所有的步驟,以3+2*5為例:從左往右掃瞄,
第1步:3進入到字尾表示式中
第2步:+進入到操作符棧中(由於操作符棧中沒有元素,所以不需要比較,直接進入即可)
第3步:2進入到字尾表示式中
第4步:開始與操作符棧的棧頂的操作符的優先順序比較,由於棧頂的操作符為+,所以的優先順序要比棧頂操作符優先順序高,直接進入棧,目前操作符棧的元素為+*
第5步:5進入到字尾表示式中
第6步:由於操作符 棧中的元素非空,所以將其全部壓入到字尾表示式中,最後字尾表示式變為325*+
第7步:3入棧
第8步:2入棧
第9步:5入棧
第10步:遇到了操作符*,所以彈出兩個數(先彈出的是第二運算元,後彈出的是第一運算元),得到結果為2*5,繼續將得到的結果壓入到棧
第11步:遇到操作符+,得到結果為3+2乘以5.
**實現
#include
#include
#include
#include
#include
#include
using
namespace std;
struct node
;string str;
//定義乙個字串,作為全域性變數
stack s;
//操作符棧
queue q;
//字尾表示式序列
map<
char
,int
> op;
void
change()
//將中綴表示式轉換為字尾表示式
q.push
(temp)
;//將這個運算元壓入到字尾表示式中
}else
//如果是操作符
temp.op=str[i]
; s.
push
(temp)
;//吧該操作符壓入到操作符棧中
i++;}
}while
(!s.
empty()
)//如果操作符棧中還有操作符,就把它彈出到字尾表示式中
}double
cal(
)//計算字尾表示式
else
//如果是操作符
else
if(cur.op==
'-')
else
if(cur.op==
'*')
else
s.push
(temp);}
}return s.
top(
).num;
//棧頂元素就是字尾表示式的值
}int
main()
}while
(!s.
empty()
)//初始化棧
change()
;//將中綴表示式轉換為字尾表示式
printf
("%.2lf\n"
,cal()
);//計算字尾表示式
}return0;
}
c 利用棧實現簡單計算器
簡單計算器 如下 include using namespace std intprio char ch 運算子優先順序判定 double oper double a,double b,char ch 進行運算 int main else else fh.pop 將左括號彈出棧 continue e...
簡單計算器(棧)
開始複習棧,這個題感覺見得很多,各種各樣的,但是核心思路就是把中綴表示式轉化為字尾表示式,我們老師說這個東西也叫作中序二叉樹轉後序二叉樹。大概實現的方式就是用棧來實現 最開始感覺沒啥思路,因為之前一直都不會這種題 論為什麼我這麼菜,之前沒有好好學過棧,知道了stl中有stack後還是方便很多 第一次...
簡單計算器 STL 棧
讀入乙個只包含 的非負整數計算表示式,計算該表示式的值。input 測試輸入包含若干測試用例,每個測試用例佔一行,每行不超過200個字元,整數和運算子之間用乙個空格分隔。沒有非法表示式。當一行中只有0時輸入結束,相應的結果不要輸出。output 對每個測試用例輸出1行,即該表示式的值,精確到小數點後...