目录
题目描述
输入两个整数序列,第一个序列表示栈的压入顺序,请判断第二个序列是或否为该栈的弹出顺序。假设压入栈的所有数字均不相等。例如序列 {1,2,3,4,5} 是某栈的压栈序列,序列 {4,5,3,2,1} 是该栈序列对应的一个弹出序列,但 {4,3,5,1,2} 就不可能是该压栈序列的弹出序列。
测试用例
- 功能测试(输入的两个数组含有多个数字或者只有一个数字;第二个数组是或者不是第一个数组表示的压入序列对应的栈的弹出序列)
- 特殊输入测试(输入两个空指针)
题目考点
- 考察应聘者对栈的理解
- 考察应聘者用举例分析复杂问题的能力
解题思路
详细见书上的表格,看了之后就很容易理解。
得到规律:
1、如果弹出序列下一个弹出的数字在栈顶,直接弹出;
2、如果弹出序列下一个弹出的数字不在栈顶,则继续把压入序列数字压入,直到把下一个弹出的数字压入栈顶为止;
3、如果所有数字都压入栈,仍然还没找到下一个弹出的数字,则该序列就不是一个可能的弹出序列。
步骤 | 操作 | 栈 | 弹出数字 | 步骤 | 操作 | 栈 | 弹出数字 |
1 | 6 | ||||||
2 | 7 | ||||||
3 | 8 | ||||||
4 | 9 | ||||||
5 | 10 |
参考解题
tip(关于空栈错误,使用peek函数的条件):
// 如果弹出序列下一个弹出的数字不在栈顶,或者空栈
这样写条件就不对了,if (popA[popAIndex] != stack.peek() || stack.empty() ) 使用peek函数的时候需要判断栈是否为空,否则出错
这样才是对的:if (stack.empty() || stack.peek() != popA[popAIndex]) 先判断了栈是否为空,再去使用peek,所以没错
import java.util.ArrayList;
import java.util.Stack;
public class Solution {
public boolean IsPopOrder(int [] pushA,int [] popA) {
// 异常
if (pushA == null || popA == null) {
return false;
}
// 定义辅助栈,两个指针,实现压入、弹出
Stack<Integer> stack = new Stack<>();
int pushAIndex = 0;
int popAIndex = 0;
// 规律判断
while (popAIndex < popA.length) {
// 如果弹出序列下一个弹出的数字不在栈顶,或者空栈
if (stack.empty() || stack.peek() != popA[popAIndex]) {
// 则继续把压入序列数字压入,直到把下一个弹出的数字压入栈顶为止;
if (pushAIndex == pushA.length) {
break;
}
stack.push(pushA[pushAIndex]);
pushAIndex++;
} else {
// 如果弹出序列下一个弹出的数字在栈顶,直接弹出;
stack.pop();
popAIndex++;
}
}
// 如果所有数字都压入栈,仍然还没找到下一个弹出的数字,则该序列就不是一个可能的弹出序列。
if (popAIndex == popA.length) {
return true;
} else {
return false;
}
}
}