【编程题目】栈的 push、pop 序列

29.栈的 push、pop 序列(栈)
题目:输入两个整数序列。其中一个序列表示栈的 push 顺序,
判断另一个序列有没有可能是对应的 pop 顺序。
为了简单起见,我们假设 push 序列的任意两个整数都是不相等的。
比如输入的 push 序列是 1、2、3、4、5,那么 4、5、3、2、1 就有可能是一个 pop 系列。
因为可以有如下的 push 和 pop 序列:
push 1,push 2,push 3,push 4,pop,push 5,pop,pop,pop,pop,
这样得到的 pop 序列就是 4、5、3、2、1。
但序列 4、3、5、1、2 就不可能是 push 序列 1、2、3、4、5 的 pop 序列。

思路:

首先,我记录了每个pop序列中每一个元素对应在push序列中的位置。这就像是把push序列强制成0 1 2 3 4...一样,这样push序列就是从小到大排列的了。

然后,观察从小到大排列的push序列,其合理的pop序列的特点。

4 5 3 2 1

记录第1个数字 并查找递增的数字 这里是 4  5  他们是递增的。

3 4 2 1 5

3 4 5 递增的

发现只要这些数字符合递增规律,那么pop序列就是合理的。且这些序列就是新加入数字后开始弹出的值。

还是拿3 4 2 1 5举例

3 是在压入1 2 3后弹出的第一个值

4 是在压入4后弹出的第一个值

5 是在压入5后弹出的第一个值

4 2 1这个递减的序列表示,没有压入新值,一直在弹出。

即,有递增序列表示有压入新的值,递减序列表示一直弹出。因为push序列时递增的,故压入的新值只能越来越大。

对于4、3、5、1、2

4 5 2 显然不满足递增关系 即压入5后不能再压入2 不是合法的pop序列

注:我没法证明,不知道是不是所有的都符合这个规律。谁能举出反例吗?

/*
29.栈的 push、pop 序列(栈)
题目:输入两个整数序列。其中一个序列表示栈的 push 顺序,
判断另一个序列有没有可能是对应的 pop 顺序。
为了简单起见,我们假设 push 序列的任意两个整数都是不相等的。
比如输入的 push 序列是 1、2、3、4、5,那么 4、5、3、2、1 就有可能是一个 pop 系列。
因为可以有如下的 push 和 pop 序列:
push 1,push 2,push 3,push 4,pop,push 5,pop,pop,pop,pop,
这样得到的 pop 序列就是 4、5、3、2、1。
但序列 4、3、5、1、2 就不可能是 push 序列 1、2、3、4、5 的 pop 序列。
start time = 16:15
end time = 17:20
*/

#include <stdio.h>

int * getlocation(int data, int * poplist, int len)
{
    for(int i = 0; i < len; i++)
    {
        if(data == poplist[i])
            return poplist + i;
    }
    return NULL;
}
bool ispop(int * pushlist, int * poplist, int len)
{
    for(int i = 0; i < len; i++) //记录pop中的数字对应push中那个位置
    {
        int * loc = getlocation(pushlist[i], poplist, len);
        if(loc != NULL)
        {
            *loc = i;
        }
        else
        {
            printf("error:the two list have different member!");
        }
    }

    int IncreaseNum2 = poplist[0];
    int IncreaseNum1;
    for(int i = 1; i < len; i++)
    {
        if(poplist[i] > poplist[i - 1])
        {
            IncreaseNum1 = IncreaseNum2;
            IncreaseNum2 = poplist[i];
            if(IncreaseNum2 < IncreaseNum1)
                return false;
        }
    }
    return true;
}

int main()
{
    int a[5] = {1,2,3,4,5};
    int b[5] = {5,3,4,2,1};
    bool is = ispop(a, b, 5);
    return 0;
}

网上答案:网上的思路惊人的一致,都是直接的建一个栈来模拟这个过程。比我的思路来的要好,计算少,又好理解。

http://blog.sina.com.cn/s/blog_a46817ff01019vtd.html

如果我们希望pop的数字正好是栈顶数字,直接pop出栈即可;如果希望pop的数字目前不在栈顶,我们就到push序列中还没有
 *
被push到栈里的数字中去搜索这个数字,并把在它之前的所有数字都push进栈。如果所有的数字都被push进栈仍然没有找到这
 *
个数字,表明该序列不可能是一个pop序列。

网上随便找了个代码,还没验证http://www.cnblogs.com/aLittleBitCool/archive/2011/03/05/1971689.html

//栈的push、pop序列

#include<iostream>
#include<stack>
const int SIZE=5;                  //定义长度
using namespace std;
bool judge(int Spush[],int Spop[]){
    stack<int> my_stack;
    int iPush=0,iPop=0;
    while(iPush<SIZE){                //当栈顶和pop相等时,将pop后的栈顶与pop之后的元素相比,直到不等
        cout<<"push "<<Spush[iPush]<<endl;         //测试
        my_stack.push(Spush[iPush]);
        while(!my_stack.empty()&&iPop!=5&&my_stack.top()==Spop[iPop]){  //小心数组越界
            cout<<"pop "<<Spop[iPop]<<endl;      //测试
            iPop++;
            my_stack.pop();
        }
        iPush++;
    }
    if(iPop==SIZE) return true;
    else return false;
}
int main(void){
    int Spush[SIZE],Spop[SIZE];
    for(int i=0;i<SIZE;i++)
        cin>>Spush[i];
    for(int i=0;i<SIZE;i++)
        cin>>Spop[i];
    if(judge(Spush,Spop)) cout<<"Yes"<<endl;
    else cout<<"No"<<endl;
    system("pause");
    return 0;
}
时间: 2024-08-28 14:44:32

【编程题目】栈的 push、pop 序列的相关文章

【编程题目】有两个序列 a,b,大小都为 n,序列元素的值任意整数,无序;(需要回头仔细研究)

32.(数组.规划)有两个序列 a,b,大小都为 n,序列元素的值任意整数,无序:要求:通过交换 a,b 中的元素,使[序列 a 元素的和]与[序列 b 元素的和]之间的差最小.例如: var a=[100,99,98,1,2,3];var b=[1,2,3,4,5,40]; 首先,目标一定是先找到n个数字,使得数字和比总和的一半小,但是最接近. 思路一:开始看这道题跟之前学的动态规划很像,就想用动态规划来解.但是....做不出来........... 必须要选一半的数字让我头都大了. 思路二:

Swift处理堆栈问题——给定两组序列,其中一个序列表示栈的push 顺序,判断另一个序列有没有可能是对应的pop 顺序

题目:输入两个整数序列.其中一个序列表示栈的push 顺序,判断另一个序列有没有可能是对应的pop 顺序.为了简单起见,我们假设push 序列的任意两个整数都是不相等的.比如输入的push 序列是1.2.3.4.5,那么4.5.3.2.1 就有可能是一个pop 系列,但序列4.3.5.1.2 就不可能是push 序列1.2.3.4.5 的pop 序列. 分析: 我们首先定义遍历push的序数i=0  遍历pop序列的序数 j =0 我们可以先遍历给出的push序列,并且时刻与pop序列的头元素p

栈 给定push序列,判断给定序列是否是pop序列 ~ 进!出!进!出!进!出!进进出出!累死我了……

题目: 输入两个整数序列.其中一个序列表示栈的push顺序,判断另一个序列有没有可能是对应的pop顺序.为了简单起见,我们假设push序列的任意两个整数都是不相等的. 比如输入的push序列是1.2.3.4.5,那么4.5.3.2.1就有可能是一个pop系列.因为可以有如下的push和pop序列:push 1,push 2,push 3,push 4,pop,push 5,pop,pop,pop,pop,这样得到的pop序列就是4.5.3.2.1.但序列4.3.5.1.2就不可能是push序列1

笔试算法题(14):整数二进制表示中的1 &amp; 判定栈的push和pop序列是否对应

出题:输入一个整数,要求计算此整数的二进制表示中1的个数 分析: 如果整数表示为k,当其是负数的时候,使用1<<i分别检测k的每一位:当其位整数的时候,则k/2表示将其二进制表示右移一位,k%2 ==0表示其是否是偶数,如果不是则说明当前二进制表示的最右边一位为1,当k==0成立的时候移位结束: 另外还可以使用'消1'的方法,如果二进制表示A为'****1000',则A-1为'****0111',也就是我们仅关注二进制表示最右边的第一个 1,这样的话A&(A-1)的结果就可以将最右边的

第29题:判断一个序列是否是另一个push序列的pop序列

github:https://github.com/frank-cq/MyTest 第29题:输入两个整数序列,其中一个序列表示栈的push顺序,判断另一个序列有没有可能是对应的pop顺序.为了简单起见,我们假设push序列的任意两个整数都是不相等的.比如输入的push序列是 1.2.3.4.5,那么4.5.3.2.1 就有可能是一个pop序列,因为可以有如下的push和pop序列:push 1, push 2, push 3, push 4,pop, push 5, pop, pop, pop

【编程题目】判断整数序列是不是二元查找树的后序遍历结果,如果是,构建该二元查找树

判断整数序列是不是二元查找树的后序遍历结果题目:输入一个整数数组,判断该数组是不是某二元查找树的后序遍历的结果.如果是返回 true,否则返回 false.例如输入 5.7.6.9.11.10.8,由于这一整数序列是如下树的后序遍历结果:8/ \6 10/ \ / \5 7 9 11因此返回 true.如果输入 7.4.6.5,没有哪棵树的后序遍历的结果是这个序列,因此返回 false. 做这个题目的时候最开始傻了,想着从前到后根据数字的大小关系判断.后来幡然醒悟,根据后序遍历的特点.序列最后一

【编程题目】颠倒栈☆

66.颠倒栈(栈).题目:用递归颠倒一个栈.例如输入栈{1, 2, 3, 4, 5},1 在栈顶.颠倒之后的栈为{5, 4, 3, 2, 1},5 处在栈顶. 思路:我自己没做出来,因为总觉得用不上递归.看了网上答案http://blog.csdn.net/cxllyg/article/details/7655935 根据里面的思路 自己照着写了一遍 /* 66.颠倒栈(栈). 题目:用递归颠倒一个栈.例如输入栈{1, 2, 3, 4, 5},1 在栈顶. 颠倒之后的栈为{5, 4, 3, 2,

iOS开发-21UINavigationController导航控制器初始化 导航控制器栈的push和pop跳转理解

(1)导航控制器初始化的时候一般都有一个根视图控制器,导航控制器相当于一个栈,里面装的是视图控制器,最先进去的在最下面,最后进去的在最上面.在最上面的那个视图控制器的视图就是这个导航控制器对外展示的界面,也就是用户看到的界面. (2)我们需要把导航控制器加载到APP中,需要把这个导航控制器设置为window的根视图控制器(都是控制器类,可以赋值),这样就相当于加载到了window里. (3)我们要在栈中新增或者删除一个视图控制器,就需要得到导航控制器,一般在栈中得所有视图控制器都有一个self.

【iOS开发-21】UINavigationController导航控制器初始化,导航控制器栈的push和pop跳转理解

(1)导航控制器初始化的时候一般都有一个根视图控制器,导航控制器相当于一个栈,里面装的是视图控制器,最先进去的在最以下,最后进去的在最上面.在最上面的那个视图控制器的视图就是这个导航控制器对外展示的界面,也就是用户看到的界面. (2)我们须要把导航控制器载入到APP中,须要把这个导航控制器设置为window的根视图控制器(都是控制器类,能够赋值),这样就相当于载入到了window里. (3)我们要在栈中新增或者删除一个视图控制器,就须要得到导航控制器,一般在栈中得全部视图控制器都有一个self.