PAT 1051. Pop Sequence

来源:互联网 发布:ubuntu wps 编辑:程序博客网 时间:2024/05/21 09:55

就是要分析清楚,数列里出现哪些情况,可以判为非法?

我是这样分的,

1:不能输出已经输出过的数,这用一个bool数组来实现。

2:当前如果要输出数字t,那么1到t都得入栈(或者入过栈,后来又出去了),我们在遍历中可以知道栈已经pop了多少个数,因为遍历过的,都是已经pop了的,所以遍历了几个就说明已经pop了几个。那么当前栈内存有的数字个数为( t - 已经pop过的数字个数 ),这个值不能超过栈的最大容量,否则判非法。

3:根据之前的输出,可以判定当时栈顶的数的值,比如前面pop了一个数t,那么栈顶就要从t-1开始往下找,如果t-1已经输出过了,就看t-2,如果t-2已经输出过了,就看t-3(是否已输出过,查询前面说的bool数组即可),这样往下找,直到找到栈顶(可能会发现栈为空)。有了之前定下来的栈顶,那么当前要输出的数,是不可以小于栈顶数值的,否则不符合“先进后出”原则。

如没有上述情况,则当前输出是合法的。如整个数列遍历结束都没有出现上述情况,整个数列就是合法的。

#include<cstdio>#include<cstring>#include<iostream>using namespace std;const int N=1005;int m,len;int check[N];bool outside[N];int main(){int i,k;scanf("%d%d%d",&m,&len,&k);while(k--){memset(outside,0,sizeof(outside));for(i=0;i<len;i++)scanf("%d",&check[i]);int last=0;for(i=0;i<len;i++){//printf("check %d\t",check[i]);if(outside[check[i]]){//不能输出已经输出过的数 //printf("condition 1\n"); break;} if(check[i]-i>m){//要输出这个数所需的栈长 不能超过m //printf("condition 2\n"); break;}if(last!=0&&check[i]<last){//若栈不为空,则不能输出比末尾小的数 //printf("condition 3\n"); break;}outside[check[i]]=true;if(check[i]>last)last=check[i];while(outside[last])last--;//printf("last=%d\n",last);}if(i>=len)printf("YES\n");elseprintf("NO\n");}return 0;}


0 0
原创粉丝点击