瞧瞧摸出我的逆波兰板子 #include<bits/stdc++.h>
using namespace std;
#define pi acos(-1)
#define mod 998244353
#define INF 0x3f3f3f
#define fi first
#define se second
#define it iterator
#define ins insert
#define mp make_pair
#define pb push_back
#define lb lower_bound
#define ub upper_bound
#define ll long long
#define ull unsigned long long
#define mem(a) memset(a,0,sizeof(a))
#define cio ios::sync_with_stdio(false)
#define gcd __gcd
ll lgcd(ll a,ll b){return b == 0? a:lgcd(b, a % b);}
int lowbit(int x){return x&(-x);}
#define T int t;scanf("%d",&t);while(t--)
#define CE cout << endl
#define C(n) cout << n << endl
#define CY cout << "YES" << endl
#define CN cout << "NO" << endl
#define Cy cout << "Yes" << endl
#define Cn cout << "No" << endl
int binaryPow(int a, int b){ // a^b%mod
int ans = 1;
while(b > 0){
if(b & 1){
ans = ans * a % mod;
}
a = a * a % mod;
b >>= 1;
}
return ans;
}
double Calculate(double a, double b, char f) // 进行加减乘除运算
{
if(f=='+') return b+a;
if(f=='-') return b-a;
if(f=='*') return b*a;
if(f=='/') return b/a;
if(f=='^') return binaryPow(b,a);
return 0;
}
int jud(char a) // 判断优先级
{
if(a=='^') return 3;
if(a=='*'||a=='/') return 2;
if(a=='-'||a=='+') return 1;
return 0;
}
int jud1(char a) // 判断运算符
{
if(a=='+'||a=='-'||a=='*'||a=='/'||a=='^') return 1;
return 0;
}
char s[500];
char r[500]; // 存储逆波兰式的结果
int k;
void ReversePolish() // 转化成逆波兰式
{
mem(r);
k = 0;
int l = strlen(s);
stack<char>q; // 临时栈(存储运算符)
for(int i = 0; i < l; i++){
if(s[i]==' ') continue; // 去掉空格干扰
if(isdigit(s[i])){ // 如果是运算数
r[k++] = s[i];
while(isdigit(s[i+1])&&i+1<l){
r[k++] = s[i+1];
++i;
}
r[k++] = ' '; // 用空格隔开
}
if(s[i]=='('){ // 左括号 直接入临时栈
q.push(s[i]);
}
if(s[i]==')'){ // 右括号 将左右括号之间运算符放进逆波兰式中
while(q.top()!='('){
r[k++] = q.top();
r[k++] = ' ';
q.pop();
}
q.pop();
}
while(jud1(s[i])==1){ // 运算符
if(q.empty()||q.top()=='('||jud(s[i])>jud(q.top())){
// 栈为空,栈顶为左括号,当前运算符优先级大于栈顶运算符入栈
q.push(s[i]);
break;
}else{
// 将栈顶运算符放进逆波兰式中
r[k++] = q.top();
r[k++] = ' ';
q.pop();
}
}
}
// 如果临时栈不为空,将剩余运算符放进逆波兰式中
while(!q.empty()){
r[k++] = q.top();
r[k++] = ' ';
q.pop();
}
cout << "Reverse Polish:";
for(int i = 0; i < k; i++) cout << r[i]; // 输出逆波兰式
CE;
}
double Result() // 计算逆波兰式
{
stack<double>re; // 存储运算数
for(int i = 0; i < k; i++){
if(isdigit(r[i])){ // 运算数直接入栈
double x = r[i++]-'0';
while(r[i]!=' '){
x = x*10+r[i++]-'0';
}
re.push(x);
}else if(jud1(r[i])==1){ // 运算符 从栈顶取两个数运算,再将结果入栈
double x1 = re.top();
re.pop();
double x2 = re.top();
re.pop();
// cout << x1 << " " << x2 << " " << r[i] << endl;
double x3 = Calculate(x1,x2,r[i]);
// cout << x3 << endl;
re.push(x3);
}
}
cout << "Result:";
return re.top();
}
int main()
{
scanf("%s", s); // 读入一个四则运算
ReversePolish(); // 转化成逆波兰式
double op = Result(); // 计算结果
printf("%.2lf\n", op);
return 0;
}
|