具体思路是从B方向的序列 倒推 栈C 的入栈出栈顺序,
以B方向的5,4,3,2,1为例子:从一个数字5开始,要想从栈C拿到5号车厢,5号车厢得入栈C,且5号车厢处于栈顶位置,为了保证5号车
厢在栈C中,必须把1,2,3,4,5(小于等于5的车厢)压入栈C中,入栈操作完毕后,然后取出栈顶元素,此时取出来的是5,和B
方向的第一个数字5一致,我们接着看B方向的第二个数字4,因为4号车厢已压入栈C中,所以不需要入栈操作,直接取出栈顶元素,
进行对比,此时取出来的栈顶元素正是4,符合要求,接下来看B方向的第三个数字3,后面就依次类推了
下面我们以5 4 1 2 3为例子:
还是从B方向的第一个数字开始,这个数字是5,所以依次把1 ,2,3,4,5压入栈C中,然后取出栈顶元素5,与B方向的第一个数字
5一致,然后校验B方向的第二个数字4,由于4已经入栈了,取出栈顶元素,取出来一看是4,符合,然后校验B方向第三个数字1,由于
4已经入栈了,取出栈顶元素,取出来一看是3,不等于数字1,所以 5 4 1 2 3 是一个非法序列。
由于station符合后进先出规则,可以用一个stack<int>来表示station。 然后采用模拟的规则来写,因为进入station是按照编号递增进入,所以可以用aId变量表示。 接下来就是模拟时候应该注意的条件,我们知道有以下两种情况,一种是一进来station,就出station 也就是 aId == coaches[lenB];一种是进来时还不出站,那么这时候就要s.push(aId)//压栈,但是这一种的条件呢? 我们如果可以排除掉第一种,那么无非就是第二种了。但是我们要知道,在进站之前,如果站台里有车它是可以先出站的 ,这种状态就条件就是 !s.empty() && s.top() == coaches[lenB].所以只要按照顺序判断这几个条件 就可以写出这个模拟程序了。
入栈 1 2 3 4 5 int A=1(静态栈顶指针)
出栈 5 4 3 2 1 int B=1(数组计数器)
将A压入栈 5 4 3 2 1 A
取栈顶元素 (A++)5 4 3 2 1== (B++)5 4 3 2 1 √
入栈 1 2 3 4 5 A
出栈 5 4 1 2 3 B
将A压入栈 5 4 3 2 1
取A栈顶元素 5==5 与B顺序对比
4==4
3!=1... ×
//特殊情况
入栈 1 2 3 4 5 A
出栈 1 2 3 4 5 B
将A压入栈 5 4 3 2 1?
//特殊情况
if(入栈顺序==出栈顺序)
向后遍历一下
if(A==t[B])
{
A++;
B++;
}
//普通情况
else if(栈非空 and 栈顶元素与出栈的火车相同)
出栈(s站
出栈的向后遍历一下(火车序号
else if( !s.empty() && s.top()==t[B] )
{
s.pop();
B++;
}
else if(栈头未遍历结束/进栈与出栈顺序不同)
将A压入栈push(A++)
else if( A<=n )
{
s.push(A);
A++; //等价s.push(A++);
}
否则不满足 No
else
{
flag=0; //不满足出栈顺序
break;
}