描述

现有一条单向单车道隧道,每一辆车从隧道的一端驶入,另一端驶出,不允许超车

该隧道对车辆的高度有一定限制,在任意时刻,管理员希望知道此时隧道中最高车辆的高度是多少

现在请你维护这条隧道的车辆进出记录,并支持查询最高车辆的功能

输入

第一行仅含一个整数,即高度查询和车辆出入操作的总次数n

以下n行,依次这n次操作。各行的格式为以下几种之一:

1. E x		//有一辆高度为x的车进入隧道(x为整数)
2. D //有一辆车离开隧道
3. M //查询此时隧道中车辆的最大高度

输出

若D和M操作共计m次,则输出m行 对于每次D操作,输出离开隧道车辆的高度 对于每次M操作,输出所查询到的最大高度

输入样例

9
E 5
E 6
M
E 2
M
D
M
D
M

输出样例

6
6
5
6
6
2

限制

0 ≤ n ≤ 2,000,000

0 ≤ x ≤ 231 - 1

保证车辆的进出序列是合法的

提示

如何由多个栈来模拟一个队列?可参考第四章末尾的某习题。

如何实现一个能够高效获取最大值的栈?

如何实现一个可以高效获取最大值的队列?

可参考第04章XA节的讲义以及《习题解析》的[10-19]题、[10-20]题


【solution】

本题的关键在于如何以较小的时间复杂度维护一个可以查询当前区间最大值的队列。

需要用到双端队列,或者说 队堆(queap)。

不妨先考虑对于栈如何来维护一个 getMax() 接口:

通过以上分析,不难写出如下AC代码(S和P均用链表来维护):

 #include <stdio.h>
#include <stdlib.h> typedef struct Node
{
int data;
struct Node *next, *pre;
}node, *pnode; typedef struct Count
{
int data, num;
struct Count *next, *pre;
}count, *pcount; int main(void)
{
pnode shead = (pnode)malloc(sizeof(node));
pnode tmp1, stail = shead; pcount phead = (pcount)malloc(sizeof(count));
pcount tmp2, ptail = phead; int n; scanf("%d", &n); for (int i = ; i < n; ++i)
{
char ch;
int x, a; do
{
ch = getchar();
} while ((ch != 'E') && (ch != 'M') && (ch != 'D')); switch (ch)
{
case 'E':
scanf("%d", &x); // x into s
tmp1 = (pnode)malloc(sizeof(node));
tmp1->data = x;
stail->next = tmp1; tmp1->pre = stail; stail = tmp1; // prepare num for x into p
a = ;
tmp2 = (pcount)malloc(sizeof(count));
ptail->next = tmp2; tmp2->pre = ptail; ptail = tmp2;
while ((ptail->pre != phead) && (ptail->pre->data <= x))
{
a += ptail->pre->num; tmp2 = ptail->pre;
tmp2->pre->next = ptail;
ptail->pre = tmp2->pre;
delete tmp2;
} // x into p
ptail->data = x; ptail->num = a; break;
case 'D':
printf("%d\n", shead->next->data);
shead = shead->next;
delete shead->pre; if (!(--(phead->next)->num))
{
phead = phead->next;
delete phead->pre;
}
break;
case 'M':
printf("%d\n", phead->next->data);
break;
}
} return ;
}

* 图片解析 来自于 xuetangx 数据结构课程 丁俊晖 老师 的《习题解析》


【Tsinghua OJ】隧道(Tunel)问题的更多相关文章

  1. 【Tsinghua OJ】灯塔(LightHouse)问题

    描述 海上有许多灯塔,为过路船只照明.从平面上看,海域范围是[1, 10^8] × [1, 10^8] . (图一) 如图一所示,每个灯塔都配有一盏探照灯,照亮其东北.西南两个对顶的直角区域.探照灯的 ...

  2. 【Tsinghua OJ】祖玛(Zuma)问题

    描述 祖玛是一款曾经风靡全球的游戏,其玩法是:在一条轨道上初始排列着若干个彩色珠子,其中任意三个相邻的珠子不会完全同色.此后,你可以发射珠子到轨 道上并加入原有序列中.一旦有三个或更多同色的珠子变成相 ...

  3. 【Tsinghua OJ】范围查询(Range)问题

    [问题描述]数轴上有n个点,对于任一闭区间 [a, b],试计算落在其内的点数. [输入]第一行包括两个整数:点的总数n,查询的次数m.第二行包含n个数,为各个点的坐标.以下m行,各包含两个整数:查询 ...

  4. 【Tsinghua OJ】多米诺骨牌(domino)问题

    (domino.c/cpp)[问题描述] 小牛牛对多米诺骨牌有很大兴趣,然而她的骨牌比较特别,只有黑色和白色的两种.她觉 得如果存在连续三个骨牌是同一种颜色,那么这个骨牌排列便是不美观的.现在她有n个 ...

  5. 【Tsinghua OJ】循环移位(Cycle)

    Description Cycle shifting refers to following operation on the sting. Moving first letter to the en ...

  6. Tsinghua OJ Zuma

    Description Let's play the game Zuma! There are a sequence of beads on a track at the right beginnin ...

  7. ACM/ICPC 之 快排+归并排序-记录顺序对(TSH OJ-LightHouse(灯塔))

    TsingHua OJ 上不能使用<algorithm>头文件,因此需要手写快排(刚开始写的时候自己就出了很多问题....),另外本题需要在给横坐标排序后,需要记录纵坐标的顺序对的数量,因 ...

  8. ACM/ICPC 之 双向链表_构造列表-模拟祖玛 (TSH OJ-Zuma(祖玛))

    这一题是TsingHua OJ上的一道题目,学堂在线的一位数据结构老师的题目(原创),所以我直接把题目先贴下来了,这道题对复习双向链表很有帮助,而且也对数据结构中List,也就是对列表的回顾也是很有帮 ...

  9. Android终端配置isatap隧道使用IPV6的方法

    使用isatap隧道可以在手机有IPV4网络的情况下访问IPv6网络资源.关于isatap隧道的配置方法,清华.上交两所学校都给出了相应的在windows xp/2003,windows 2000,以 ...

随机推荐

  1. 《javascript高级程序设计》第八章 The Browser Object Model

    8.1 window 对象 8.1.1 全局作用域 8.1.2 窗口关系及框架 8.1.3 窗口位置 8.1.4 窗口大小 8.1.5 导航和打开窗口 8.1.6 间歇调用和超时调用 8.1.7 系统 ...

  2. (01)odoo8.0_Ubuntu14.04源码安装

    作者:陈伟明联系 :  QQ 942923305 | 微信 toby942923305E-mail: toby2chen@hotmail.com============================ ...

  3. Java 集合系列 02 Collection架构

    java 集合系列目录: Java 集合系列 01 总体框架 Java 集合系列 02 Collection架构 Java 集合系列 03 ArrayList详细介绍(源码解析)和使用示例 Java ...

  4. Mysql复制表格

    1.复制表结构及数据到新表 CREATE TABLE 新表 as SELECT * FROM 旧表 不过这种方法的一个最不好的地方就是新表中没有了旧表的primary key.Extra(auto_i ...

  5. [转]Integer.valueOf(String) 方法之惑

    具体问题以前偶然遇到过,好象是一个java答题得分的论坛,当时做错还研究了下怎么回事,但是前两天遇到类似问题却没想起来.巩固下基础,转了下面文章. 以下内容转自:http://www.importne ...

  6. ExecuteNonQuery()返回值注意点

    在使用ExecuteNonQuery(),调用存储过程,语句执行无错误,但是返回结果一直是-1 原因: 当使用储存过程时, 要把SET NOCOUNT ON  这个语句去掉, 这样数据就有反回值了 当 ...

  7. java 面向对象编程--第17章 I/O系统

    1.I/O操作指的是输入和输出流的操作.相对内存而言,当我们从数据源中将数据读取到内存中,就是输入流,也叫读取流.当我们将内存中处理好的数据写入数据源,就是输出流,也叫写入流. 2.流按照内容分类:字 ...

  8. Resume Hook SSDT

    在HookSSDT中  通过在第4部通过索引将NtOpenProcess 换成 Base[索引] = FakeNtOpenProcess; so 在阻止时应该在ntoskrnl.exe 找到真正的Op ...

  9. ASP.NET MVC 4使用Bundle的打包压缩JS/CSS

    打包(Bundling)及压缩(Minification)指的是将多个js文件或css文件打包成单一文件并压缩的做法,如此可减少浏览器需下载多个文件案才能完成网页显示的延迟感,同时通过移除JS/CSS ...

  10. redis学习(一)

    一.redis简介 Redis是基于内存.可持久化的日志型.key-value高性能存储系统.关键字(Keys)是用来标识数据块.值(Values)是关联于关键字的实际值,可以是任何东西.有时候你会存 ...