这题花了我近三个小时,本地AC评测就会RE两个点,心累……
这题当然是模拟,但是要考虑的东西很多,所以这题是一道蓝题。
1.首先考虑一下为什么会ERR:
1)有F而没有E
2)有E而没有F
3)变量用过了
看见前两个条件就非常自如的联想到了栈。
bool ok=true; int word[30]; if(word[i-'a'+1]!=0) word[i-'a'+1]=0; else ok=false; if(p<0) ok=false;//p是指针 if(ok==false) {printf("ERR\n");continue;}
2.再考虑一下计算复杂度
1)前为n且后为n -> 复杂度常数级别
2)前为n且后不为n -> 复杂度常数级别
3)前不为n且后为n -> 复杂度n级别
4)前不为n且后不为n -> 复杂度常数级别
5)如果在这条循环之前有一条循环不执行(前不为n且后为n或者说两个常数前面的比后面的大)-> 复杂度常数级别
for(int j=0;j<len;j++) { if(s[j]>e[j]&&s[j]>='0'&&s[j]<='9'&&e[j]>='0'&&e[j]<='9') {wyq=true;break;} if(s[j]<e[j]&&s[j]>='0'&&s[j]<='9'&&e[j]>='0'&&e[j]<='9') break; }//若都是常数,进行比较 if(strlen(s)>strlen(e)&&s[0]>='0'&&s[0]<='9'&&e[0]>='0'&&e[0]<='9') h[p+1].lxp=true; if(wyq||(s[0]=='n'&&e[0]!='n')) h[p+1].lxp=true;//判断代码是否有运行
for(int k=1;k<=p+1;k++) if(h[k].lxp==true) {h[++p].data='1';h[p].old=i;wyc=true;break;}//前面的比后面的大,当作是常数级别 if(wyc) continue; if(s[0]=='n'&&e[0]=='n') {h[++p].data='1';h[p].old=i;} if(s[0]=='n'&&e[0]!='n') {h[++p].data='1';h[p].old=i;} if(s[0]!='n'&&e[0]=='n') {h[++p].data='n';h[p].old=i;} if(s[0]!='n'&&e[0]!='n') {h[++p].data='1';h[p].old=i;}
3.再然后就是最后的判断和最开始的初始化
感觉没什么问题可还是RE了
上代码
#include<bits/stdc++.h> using namespace std; int t,p=0; struct node{ char data; char old; int maxn;//用来储存栈中第i层最大的时间复杂度 bool lxp;//判断代码是否有运行 }h[110];//栈,看是否匹配 int l,word[30];//word是看这个变量用过没有 char o[50]; int num=0,sum=0; int main() { // freopen("hh1.in","r",stdin); // freopen("hh1.out","w",stdout); scanf("%d",&t); while(t--) { for(int k=0;k<=109;k++) {h[k].maxn=1;h[k].data=0;h[k].old=0;h[k].lxp=false;} for(int i=0;i<=29;i++) word[i]=1; sum=1;p=0;num=0;//每条程序重置一次 scanf("%d%s",&l,o); bool flag=false;//判断是常数还是n^w bool ok=true; if(strlen(o)==4) flag=true; else { int n=strlen(o); for(int i=0;i<n;i++) if(o[i]<='9'&&o[i]>='0') num=num*10+o[i]-'0'; } while(l--) { char c,i,s[15],e[15]; cin>>c; if(c=='F') { sum=1;//将指数重置 cin>>i>>s>>e; bool wyq=false,wyc=false;//临时变量,不用管意义 int len=strlen(s); for(int j=0;j<len;j++) { if(s[j]>e[j]&&s[j]>='0'&&s[j]<='9'&&e[j]>='0'&&e[j]<='9') {wyq=true;break;} if(s[j]<e[j]&&s[j]>='0'&&s[j]<='9'&&e[j]>='0'&&e[j]<='9') break; }//若都是常数,进行比较 if(strlen(s)>strlen(e)&&s[0]>='0'&&s[0]<='9'&&e[0]>='0'&&e[0]<='9') h[p+1].lxp=true; if(wyq||(s[0]=='n'&&e[0]!='n')) h[p+1].lxp=true;//判断代码是否有运行 if(word[i-'a'+1]!=0) word[i-'a'+1]=0; else ok=false; for(int k=1;k<=p+1;k++) if(h[k].lxp==true) {h[++p].data='1';h[p].old=i;wyc=true;break;}//前面的比后面的大,当作是常数级别 if(wyc) continue; if(s[0]=='n'&&e[0]=='n') {h[++p].data='1';h[p].old=i;} if(s[0]=='n'&&e[0]!='n') {h[++p].data='1';h[p].old=i;} if(s[0]!='n'&&e[0]=='n') {h[++p].data='n';h[p].old=i;} if(s[0]!='n'&&e[0]!='n') {h[++p].data='1';h[p].old=i;} } if(c=='E') { if(h[p].data==0) p--; if(h[p].data=='n') sum=h[p+1].maxn+1;//前一层为n^1级别的就指数+1 else sum=h[p+1].maxn*1; h[p].maxn=max(sum,h[p].maxn);//存储到这时最大的指数 h[p+1].maxn=1; word[h[p].old-'a'+1]=1; h[p].lxp=false; p--; if(p<0) ok=false; } } if(ok==false) {printf("ERR\n");continue;}//如果变量用过了或括号不匹配,错误,跳出去 if(p>0) {printf("ERR\n");continue;} if(flag&&h[1].maxn==1) printf("Yes\n"); else if(!flag&&h[1].maxn-1==num) printf("Yes\n"); else printf("No\n"); } return 0; }