题目
按照1到N的顺序入栈,但是不知道什么时候出栈,给你一列数,问你有没有可能是出栈序列
#include<stack>
#include<iostream>
#include<string>
#include<vector>
#include<cstring>
using namespace std;
bool ARR[10007];//验证是否出过栈的bool数组
bool find_go(int n, int m, vector<int>& arr, bool* ARR) {//用for循环查找在n到m之间是否有没出过栈的
int i;
for (i = n + 1; i <= m; i++) {
//cout << "i=" << i << endl;
//cout << "当前tf值"<< ARR[i] << endl;
if (!ARR[i])
return false;
}
return true;
}
int main() {
vector<int>arr;
int n;
int temp;
int t;
int i;
while (cin >> n) {
int time_go = 0;
bool ye = true;
if (!n)
break;
while (n--) {
cin >> temp;
arr.push_back(temp);
}
t = arr[0];
ARR[t] = true;
for (i = 1; i < arr.size(); i++) {
if (arr[i] > t) {//后面出栈的如果比前面出栈的大,那就不需要判断,肯定合理。
t = arr[i];
ARR[t] = true;
//cout << "当前被处理元素=" << arr[i]<<endl;
continue;
}
if (arr[i] < t) {//如果后面出栈的比前面出栈的小,那么需要看一下在二者之间是否有没出栈的,有的话说明该序列不可能
//是可能的出栈序列
//cout << "当前被处理元素=" << arr[i] << endl;
if (find_go(arr[i], t, arr, ARR)) {
t = arr[i];
ARR[t] = true;
continue;
}
else {
cout << "No" << endl;
ye = false;
break;
}
}
}
if (ye)
cout << "Yes" << endl;
arr.clear();
memset(ARR, 0, sizeof(ARR));
}
return 0;
}
先把代码贴上来
还是把样例拿来吧
输入:
5
3 4 2 1 5
5
3 5 1 4 2
输出:
Yes
No
好,可以开始讨论了:第一个出栈是啥都无所谓,关键看的是后续出栈的元素和前一个出栈的元素之间关系:如果前一个出栈的元素大于后一个元素,那就不需要判断了,肯定可以,就是往里面塞入元素,然后出栈就是比方说第一个样例,第一个出栈的是3,第二个是4,就是3出来了然后4入栈再出栈
但是如果后续的元素比前面的小,那就要考虑在二者之间的元素是不是已经出栈了,比方说1 2 3按顺序入栈然后3出栈,要想1出栈,2必须先出栈,因为2后于1入栈,栈是后入先出的。
那就跑个数组看一下就是,也就是下面这段代码的来历
bool find_go(int n, int m, vector<int>& arr, bool* ARR) {//用for循环查找在n到m之间是否有没出过栈的
int i;
for (i = n + 1; i <= m; i++) {//n是小数,m是大数
if (!ARR[i])
return false;
}