1. // hdu5033 Building 单调队列
  2. //
  3. // 题目大意:
  4. //
  5. // n栋大楼,有一个高度h和位置x。如今有一个人高度为0,有q个询问
  6. // 每一个询问有一个位置x,求在位置x能看到天空的最大的角度。
  7. //
  8. // 解题思路:
  9. //
  10. // 首先得想到将q个询问的位置作为一栋大楼放在整个大楼中考虑。这样
  11. // 问题就比較一致,也比較easy处理啦。
  12. //
  13. // 想象一下,每次从左往右走,对于当前位置的左半边的90度内,看天的角度是
  14. // 逐渐减小的,这样。假设当前位置的左边比当前位置要低,那么当前位置就挡住了
  15. // 之前的更矮的。也就是说之后的位置是不可能看到比当前更矮的大楼了,这样。就可
  16. // 以看成是一个单调的序列。序列中元素高度单调递减,即所谓的单调队列。
  17.  
  18. 但仅仅仅仅是
  19. // 这样是不够的。也会存在比当前元素(设为h)高设为h1,在队列中h1前面的元素是h2,尽管
  20. // h1是比h大,可是假设顺着h1的高度看过去。会被h2挡住。这时h1是没有作用的。也要将
  21. // 这个元素从队列中移除。
  22. //
  23. // 当遇到的大楼要查询的位置的时候,此时队列最后的一个元素并不一定是最优的值,由于
  24. // 这种值可能是不合法的。比方上面的h1会被h2挡住。并不会看到天空。
  25.  
  26. 照样移除这种元素
  27. // 最后,队列的最后一个元素就是解。
  28. //
  29. // 右边的问题全然能够转化为左边的问题,仅仅是从右往左处理而已。
  30.  
  31. //
  32. //
  33. // 感悟:
  34. //
  35. // 这道题是14年北京区的网赛的一道题目,当时的我尽管看懂了题目的意思。可是真的全然不会做。
  36. // 直到如今伟大的MW大咖,说是单调队列能够做,我就做了。可是卡了一天半,还是想不出来详细怎么解
  37. // 首先将询问的位置当作大楼这一点我想到了,维持高度递减的单调队列我想到了,就是最后一种情况没有
  38. // 想到,更不知道要怎么处理,在伟大的MW大咖的敦敦教诲还有耐心的提示下。最终最终想到了解决的办法
  39. // 不easy啊不easy。在此真诚感谢MW大咖~
  40. //
  41. // 过程无疑会有非常多的疑惑,一个地方不慎。满盘皆输,找到一处的错误。心里十分的欣喜,特别是在ac
  42. // 之后。那种心情。实在是难以描写叙述。感觉到自己的付出,真的是有回报。曾经不懂的东西,自己认真学
  43. // 总会有收获。哪怕收获是那么一点点,微不足道,但收获就是收获,没有这个能让人更加欣喜啦,痛苦并快乐着
  44. // 十分的享受。还是那句话,继续练吧~~~
  45.  
  46. #include <cstdio>
  47. #include <algorithm>
  48. #include <cmath>
  49. #include <iostream>
  50. #include <cstring>
  51. using namespace std;
  52.  
  53. const int MAX_N = 2e5 + 9;
  54.  
  55. const double PI = acos(-1.0);
  56. int n,q;
  57. double deqh[MAX_N];
  58. double deqx[MAX_N];
  59. double angle[MAX_N];
  60.  
  61. struct node {
  62. double pos;
  63. double h;
  64. int id;
  65.  
  66. node(){
  67.  
  68. }
  69.  
  70. node(double pos,double h,int id):pos(pos),h(h),id(id){
  71.  
  72. }
  73. };
  74.  
  75. node sky[MAX_N];
  76.  
  77. bool cmp(node a,node b){
  78. return a.pos < b.pos;
  79. }
  80.  
  81. void input(){
  82. scanf("%d",&n);
  83. double x,h;
  84. for (int i = 1;i <= n;i++){
  85. scanf("%lf%lf",&x,&h);
  86. sky[i] = node(x,h,0);
  87. }
  88. scanf("%d",&q);
  89.  
  90. for (int i = 1;i <= q;i++){
  91. scanf("%lf",&x);
  92. sky[i+n] = node(x,0.0,i);
  93. angle[i] = 0.0;
  94. }
  95.  
  96. n += q;
  97.  
  98. sort(sky+1,sky+n+1,cmp);
  99. }
  100.  
  101. double getk(double a,double b){
  102. return fabs(a/b);
  103. }
  104.  
  105. void getleft(){
  106. int head,tail;
  107. head = tail = 0;
  108. for (int i=1;i<=n;i++){
  109. if (sky[i].id){
  110. while(head + 1 < tail){
  111. double k1 = getk(deqh[tail-1],deqx[tail-1]-sky[i].pos);
  112. double k2 = getk(deqh[tail-2],deqx[tail-2]-sky[i].pos);
  113. if (k1 <= k2)
  114. tail--;
  115. else break;
  116. }
  117. angle[sky[i].id] += atan(deqh[tail-1]/fabs(deqx[tail-1]-sky[i].pos));
  118. }else {
  119.  
  120. while(head < tail && deqh[tail-1] < sky[i].h)
  121. tail--;
  122.  
  123. while(head + 1 < tail){
  124. double k1 = getk(deqh[tail-1]-sky[i].h,deqx[tail-1]-sky[i].pos);
  125. double k2 = getk(deqh[tail-2]-sky[i].h,deqx[tail-2]-sky[i].pos);
  126. if (k1 <= k2)
  127. tail--;
  128. else
  129. break;
  130. }
  131. deqh[tail] = sky[i].h;
  132. deqx[tail++] = sky[i].pos;
  133. }
  134. }
  135. }
  136.  
  137. void getright(){
  138. int head,tail;
  139. head = tail = 0;
  140. for (int i = n;i >= 1;i--){
  141. if (sky[i].id){
  142. while(head + 1 < tail){
  143. double k1 = getk(deqh[tail-1],deqx[tail-1]-sky[i].pos);
  144. double k2 = getk(deqh[tail-2],deqx[tail-2]-sky[i].pos);
  145. if (k1 <= k2)
  146. tail--;
  147. else
  148. break;
  149. }
  150.  
  151. angle[sky[i].id] += atan(deqh[tail-1]/fabs(deqx[tail-1]-sky[i].pos));
  152.  
  153. }else {
  154. while(head < tail && deqh[tail-1] < sky[i].h)
  155. tail--;
  156.  
  157. while(head + 1 < tail){
  158.  
  159. double k1 = getk(deqh[tail-1]-sky[i].h,deqx[tail-1] - sky[i].pos);
  160. double k2 = getk(deqh[tail-2]-sky[i].h,deqx[tail-2] - sky[i].pos);
  161.  
  162. if (k1 <= k2){
  163. tail--;
  164. }else
  165. break;
  166.  
  167. }
  168. deqh[tail] = sky[i].h;
  169. deqx[tail++] = sky[i].pos;
  170. }
  171. }
  172. }
  173.  
  174. void solve(){
  175. getleft();
  176. getright();
  177. for (int i=1;i<=q;i++){
  178. printf("%.10lf\n",(PI - angle[i]) * 180.0 / PI);
  179. }
  180. }
  181.  
  182. int main(){
  183. int t;
  184. //freopen("1.txt","r",stdin);
  185. scanf("%d",&t);
  186. int kase = 1;
  187. while(t--){
  188. input();
  189. printf("Case #%d:\n",kase++);
  190. solve();
  191. }
  192. }

hdu5033 Building 单调队列的更多相关文章

  1. HDU5033 building 单调栈+计算几何

    正解:单调栈 解题报告: 哇生气辽QAQ本来打了半天feel good都快调出来了然后说换题了QAQ(所以可能那题的代码会过一阵子再放上来了QAQ 不过还是大爆手速打了一通拿到首杀了嘻嘻 美滋滋辽 然 ...

  2. HDU5033 Building(单调栈)

    题意是说在水平轴上有很多建筑物(没有宽度),知道每个建筑物的位置与高度.有m个查询,每次查询位置x所能看到的天空的角度. 方法是将建筑与查询一起排序,从左往右计算一遍,如果是建筑物,则比较最后两个(当 ...

  3. hdu5033 Building (单调栈+)

    http://acm.hdu.edu.cn/showproblem.php?pid=5033 2014 ACM/ICPC Asia Regional Beijing Online B 1002 Bui ...

  4. [hdu5033]单调队列

    题意:x轴上有n棵树,询问你站在某个点的视角.从左至右,单调队列(类似凸包)维护下.我强迫症地写了个模板QAQ #include <iostream> #include <cstdi ...

  5. BestCoder Round #89 B题---Fxx and game(单调队列)

    题目链接 http://acm.hdu.edu.cn/showproblem.php?pid=5945     问题描述 输入描述 输出描述 输入样例 输出样例 题意:中文题,不再赘述: 思路:  B ...

  6. 单调队列 && 斜率优化dp 专题

    首先得讲一下单调队列,顾名思义,单调队列就是队列中的每个元素具有单调性,如果是单调递增队列,那么每个元素都是单调递增的,反正,亦然. 那么如何对单调队列进行操作呢? 是这样的:对于单调队列而言,队首和 ...

  7. FZU 1914 单调队列

    题目链接:http://acm.fzu.edu.cn/problem.php?pid=1914 题意: 给出一个数列,如果它的前i(1<=i<=n)项和都是正的,那么这个数列是正的,问这个 ...

  8. BZOJ 1047 二维单调队列

    题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=1047 题意:见中文题面 思路:该题是求二维的子矩阵的最大值与最小值的差值尽量小.所以可以考 ...

  9. 【BZOJ3314】 [Usaco2013 Nov]Crowded Cows 单调队列

    第一次写单调队列太垃圾... 左右各扫一遍即可. #include <iostream> #include <cstdio> #include <cstring> ...

随机推荐

  1. AS常见的错误

    导入的项目使用的gradle版本和本地的要一致,不然会提示类似"Minimum supported Gradle version is 3.3. Current version is 2.1 ...

  2. tcMalloc 配置和优化 nginx 高性能

    tcMalloc优化nginx  记住:nginx一定要先启动 1>下载安装libunwind: #wget  http://download.savannah.gnu.org/releases ...

  3. 【翻译自mos文章】 11gR1版本号 asmcmd的新命令--cp、md_backup、md_restore

    11gR1版本号 asmcmd的新命令--cp.md_backup.md_restore 參考原文: ASMCMD - New commands in 11gR1 (Doc ID 451900.1) ...

  4. MyEclipse改动内存大小

    方式一网上说的(没有測试过): 找到MyEclipse的安装文件夹,一般假设不改动的话默觉得C:\MyEclipse10.1\Genuitec\MyEclipse 10.1有一个myeclipse.i ...

  5. RecyclerView实现底部载入很多其它功能

    这两天在公司没有什么任务分配,就研究了下咱们Google在Android5.0 推出的一个用来取代ListView的列表控件----RecyclerView. 发现功能上确实比ListView强大了不 ...

  6. python fuzzy c-means demo

    摘自:http://pythonhosted.org/scikit-fuzzy/auto_examples/plot_cmeans.html#example-plot-cmeans-py,加入了自己的 ...

  7. Python学习历程之面对对象浅识

    # ===============================封装====================================# class Bar:# def __init__(se ...

  8. 6.vi使用

  9. centos7安装mysql(转载)

    Centos7安装并配置mysql5.6完美教程 Centos7将默认数据库mysql替换成了Mariadb,对于我们这些还想使用mysql的开发人员来说并不是一个好消息.然而,网上关于Linux安装 ...

  10. 将查询到的数据导出到Excel终结版

    吐槽 最近新项目需要用到导出数据到Excel,试了试之前写的一篇博文,但是感觉那个不太好,主要原因是没能实现样式控制,今天我们就来介绍一种新的导出Excel方法,而且这种方法很轻量级,它利用xml生成 ...