很自然的会想到贪心,贪心法则为,最大值=先加在乘,最小值=先乘再加,试着证明一下。
a+b*c这个式子,我们只有两种做法,即a+(b*c)和(a+b)*c,明显看到,第二个式子为a*c+b*c因为c至少为1,所以第二个式子大于等于前者。归纳法完成迭代部分即可。
WA了一次,原因是UVA输出用了%I64d,换成%lld即可。
#include <stdio.h>
#include <string.h>
char exp[50];
long long num[15];
char op[15];
int sop,snum;
long long solve(int wa,int wm)
{
sop=snum=0;
int i,len=strlen(exp),tnum=0;
for(i=0;i<=len;i++){
if(exp[i]>='0'&&exp[i]<='9') tnum=tnum*10+exp[i]-'0';
else{
num[snum++]=tnum;
if(!exp[i]) break;
tnum=0;
if(!sop) {op[sop++]=exp[i];continue;}
int wtop=(op[sop-1]=='+'?wa:wm);
int wnow=(exp[i]=='+'?wa:wm);
while(wtop>wnow){
sop--;
long long ta=num[--snum],tb=num[--snum];
if(op[sop]=='+') num[snum++]=ta+tb;
else num[snum++]=ta*tb;
if(!sop) break;
wtop=(op[sop-1]=='+'?wa:wm);
}
op[sop++]=exp[i];
}
}
while(sop){
sop--;
long long ta=num[--snum],tb=num[--snum];
if(op[sop]=='+') num[snum++]=ta+tb;
else num[snum++]=ta*tb;
}
return num[0];
}
int main()
{
int T;
scanf("%d",&T);
while(T--){
scanf("%s",exp);
printf("The maximum and minimum are %lld and %lld.\n",solve(1,0),solve(0,1));
}
return 0;
}