您的位置:首页 > 其它

HDU 5818 (多校 7) 模拟

2016-08-10 12:03 253 查看
题意:对栈的操作,有两个栈a,b然后接下来n组操作包括入栈,出栈,合并栈。合并栈按入栈的时间顺序进行排序。

官方题解:比较简单巧妙的一个做法是引入一个新的栈C,每次合并的时候就把A和B合并到C上,然后把A和B都清空. push还是按正常做,pop注意当遇到要pop的栈为空时,因为题目保证不会对空栈进行pop操作,所以这时应直接改为对C栈进行pop操作. 这样做因为保证每个元素最多只在一次合并中被处理到,pop和push操作当然也是每个元素只做一次,所以总复杂度是O(N)的. 另一种做法是用链表来直接模拟,复杂度也是O(N),但代码量稍大一些.

解题思路:比赛时怎么想都想不出来,一直只想着是要合并两个栈,但强行排序肯定是会TLE的,看了题解之后才知道原来这么简单,还是自己太弱了。直接用三个数组进行模拟了一下。

AC代码:

#include <iostream>
#include <stdio.h>
#include <cmath>
#include <cstring>
#include <algorithm>
#include <queue>
#include <map>
#include <stack>

using namespace std;
#define ll long long
#define maxn 100050

struct test
{
int  val;
int  pos;
};

test a[maxn];
test b[maxn];
test c[maxn];

int main()
{
int n;
char str1[10];
char str2[5];
char str3[5];
int cas=1;
int num;
int ida,idb,idc;
while(~scanf("%d",&n) && n!=0)
{
ida=0;
idb=0;
idc=0;
int cnt=1;///表示入栈的时间
printf("Case #%d:\n",cas++);
for(int i=0;i<n;i++)
{
scanf("%s%s",str1,str2);
if(str1[1]=='u')///入队操作
{
scanf("%d",&num);
if(str2[0]=='A')
{
a[ida].val=num;
a[ida++].pos=cnt++;
}
else
{
b[idb].val=num;
b[idb++].pos=cnt++;
}
}
else if(str1[1]=='e')///合并操作
{
scanf("%s",str3);
int ia=0,ib=0;
while(ia<ida&&ib<idb)
{
if(a[ia].pos<b[ib].pos)///比较a,b栈中时间小的入栈
{
c[idc].pos=a[ia].pos;
c[idc++].val=a[ia++].val;
}
else
{
c[idc].pos=b[ib].pos;
c[idc++].val=b[ib++].val;
}
}
while(ia<ida)
{
c[idc].pos=a[ia].pos;
c[idc].val=a[ia++].val;
idc++;
}
while(ib<idb)
{
c[idc].pos=b[ib].pos;
c[idc++].val=b[ib++].val;
}
ida=0; idb=0;
}
else if(str1[1]=='o')///出队操作
{
if(str2[0]=='A')
{
if(ida==0)
printf("%d\n",c[--idc].val);
else
printf("%d\n",a[--ida].val);
}
else
{
if(idb==0)
printf("%d\n",c[--idc].val);
else
printf("%d\n",b[--idb].val);
}
}
}
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  模拟 多校 acm hdu