PAT甲级1057 Stack (30分)|C++实现

一、题目描述

原题链接
在这里插入图片描述

Input Specification:

在这里插入图片描述

​​Output Specification:

在这里插入图片描述

Sample Input:

17
Pop
PeekMedian
Push 3
PeekMedian
Push 2
PeekMedian
Push 1
PeekMedian
Pop
Pop
Push 5
Push 4
PeekMedian
Pop
Pop
Pop
Pop

Sample Output:

Invalid
Invalid
3
2
2
1
2
4
4
5
3
Invalid

二、解题思路

对于题目这个数据量,如果每次都要进行排序,是会超时的,所以我们得想一下别的方法来找到符合题意的数据。我们这里可以采用分块的思想, 1 0 5 10^5 105这个数量级,我们一般分为316块,每一块表示数据在对应范围内出现的数目。如block[0]表示在0~315范围内元素的总数目。然后用数组table表示每个元素出现的总次数。详情请参考代码注释。

参考链接:@julia7_ 的解法

三、AC代码

#include<iostream>
#include<cstdio>
#include<cstring>
#include<stack>
using namespace std;
const int maxn = 100010;
const int sqrN = 316;
stack<int> st;  //建立堆栈
int block[sqrN];    //分块,对应每一块的元素个数
int table[maxn];    //对应元素当前的个数
void peekMedian(int K)
{
    
    
    int sum = 0;
    int idx = 0;
    while(sum + block[idx] < K) sum += block[idx++];    //计算块中所有元素的数目
    int num = idx*sqrN; //下一块的第一个
    while(sum + table[num] < K) sum += table[num++];    //计算第K个元素
    printf("%d\n", num);
}
void Push(int x)
{
    
    
    st.push(x);
    block[x/sqrN]++;    //对应块的元素数目+1
    table[x]++; //对应数目+1
}
void Pop()
{
    
    
    int x = st.top();
    st.pop();
    block[x/sqrN]--;    //对应块的元素数目-1
    table[x]--; //对应数目-1
    printf("%d\n", x);
}
int main()
{
    
    
    int x, query;
    memset(block, 0, sizeof(block));
    memset(table, 0, sizeof(table));
    char cmd[20];
    scanf("%d", &query);
    for(int i=0; i<query; i++)
    {
    
    
        scanf("%s", cmd);
        if(strcmp(cmd, "Push") == 0)
        {
    
    
            scanf("%d", &x);
            Push(x);
        }
        else if(strcmp(cmd, "Pop") == 0)
        {
    
    
            if(st.empty())  printf("Invalid\n");
            else    Pop();
        }
        else
        {
    
    
            if(st.empty())  printf("Invalid\n");
            else
            {
    
    
                int K = st.size();
                if(K%2 == 1)    K = (K+1)/2;
                else    K = K/2;
                peekMedian(K);
            }
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/weixin_42393947/article/details/108635281