4237: 稻草人

Time Limit: 40 Sec  Memory Limit: 256 MB
Submit: 1352  Solved: 594
[Submit][Status][Discuss]

Description

JOI村有一片荒地,上面竖着N个稻草人,村民们每年多次在稻草人们的周围举行祭典。
有一次,JOI村的村长听到了稻草人们的启示,计划在荒地中开垦一片田地。和启示中的一样,田地需要满足以下条件:
田地的形状是边平行于坐标轴的长方形;
左下角和右上角各有一个稻草人;
田地的内部(不包括边界)没有稻草人。
给出每个稻草人的坐标,请你求出有多少遵从启示的田地的个数

Input

第一行一个正整数N,代表稻草人的个数
接下来N行,第i行(1<=i<=N)包含2个由空格分隔的整数Xi和Yi,表示第i个稻草人的坐标

Output

输出一行一个正整数,代表遵从启示的田地的个数

Sample Input

4
0 0
2 2
3 4
4 3

Sample Output

3

所有点按y坐标排序之后进行CDQ分治,对于当前区间[L, R]过程如下图

①区间[L, mid]和区间(mid, R]先单独按x从小到大排序,

②对于区间[L, mid]维护一个纵坐标递减的单调栈s1,对于区间(mid, R]维护一个纵坐标递增的单调栈s2

对于栈s2,暴力枚举栈内相邻两个元素,在栈s1中二分出在这两个元素中间的点有多少个并加进答案

如上图,所有红点是当前在栈中的点,假设当前暴力到点a和b,那么就相当于在下面那个绿矩形中找出横坐标在点a和点b中间的点有多少个,结果显而易见为2个(红色矩阵中那两个点),ans += 2

#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
#define LL long long
typedef struct Res
{int x, y;bool operator < (const Res &b) const{if(y<b.y)return 1;return 0;}
}Res;
Res s[200005], s1[200005], s2[200005];
LL ans;
int p[200005], q[200005];
bool comp(Res a, Res b)
{if(a.x<b.x)return 1;return 0;
}
void CDQ(int l, int r)
{int m, i, p, top, t2, L, R, mid;if(l==r)return;m = (l+r)/2;CDQ(l, m);CDQ(m+1, r);sort(s+l, s+m+1, comp);sort(s+m+1, s+r+1, comp);p = l, top = t2 = 0;s2[0].x = -10000;for(i=m+1;i<=r;i++){while(top>=1 && s1[top].y>s[i].y)top--;s1[++top] = s[i];while(p<=m && s[p].x<s[i].x){while(t2>=1 && s2[t2].y<s[p].y)t2--;s2[++t2] = s[p++];}L = 0, R = t2;while(L<R){mid = (L+R)/2;if(s2[mid].x<s1[top-1].x)L = mid+1;elseR = mid;}if(s2[R].x<s1[top-1].x)R++;ans += t2-R+1;}
}
int main(void)
{int n, i;scanf("%d", &n);for(i=1;i<=n;i++){scanf("%d%d", &s[i].x, &s[i].y);p[i] = s[i].x;}sort(p+1, p+n+1);for(i=1;i<=n;i++)s[i].x = lower_bound(p+1, p+n+1, s[i].x)-p;sort(s+1, s+n+1);CDQ(1, n);printf("%lld\n", ans);return 0;
}
/*
6
0 2
2 1
4 0
1 10
3 11
5 12
*/

bzoj 4237: 稻草人(CDQ分治+单调栈+二分)相关推荐

  1. Loj#2880-「JOISC 2014 Day3」稻草人【CDQ分治,单调栈,二分】

    正题 题目链接:https://loj.ac/problem/2880 题目大意 给出平面上的nnn个点,然后求有多少个矩形满足 左下角和右上角各有一个点 矩形之间没有其他点 1≤n≤2×105,1≤ ...

  2. bzoj 4237: 稻草人 cdq分治

    求有多少个点对  其一个点为左下角  一个点为右下角所形成的矩形内部没有点 每个x与y都不同 一开始的思路: 先按照x坐标排序  进行cdq分治 然后在cdq内对y进行排序  枚举mid+1-r的点作 ...

  3. BZOJ 2388--旅行规划(分块单调栈二分)

    2388: 旅行规划 Time Limit: 50 Sec  Memory Limit: 128 MB Submit: 405  Solved: 118 [Submit][Status][Discus ...

  4. CDQ 分治与整体二分

    CDQ 分治与整体二分 CDQ 分治 主要是一种分治思想,常用于解决偏序问题. 例如三维偏序问题,我们采用的方法是先处理以第一关键字为区分的左区间.右区间内的答案,再处理左右区间互不干涉的答案. 四维 ...

  5. [CDQ分治与整体二分]个人对CDQ分治与整体二分的理解

    在线/离线:首要考虑 在线算法: 可以以序列化的方式一个一个的处理输入,不必事先知道所有输入数据 离线算法: 必须事先知道所有的输入数据 (例如选择排序就是一个离线算法,而插入排序则不是) 众所周知, ...

  6. 【cdq分治】cdq分治与整体二分学习笔记Part1.整体二分

    之所以把cdq分治和整体二分放在一起学习,是因为他们两个实在太像了-不管是做法还是代码- 感觉整体二分可能会比cdq分治稍微简单那么一点点?所以先学整体二分. 整体二分是对答案进行二分,其具体操作如下 ...

  7. cdq分治和整体二分

    cdq分治 ps:先膜拜陈丹琦大神,Orz%%%. 作用 很多动态的题目都需要高级数据结构,代码量很大,这时候cdq分治就展现了它的强大.只要不强制在线,cdq分治就可以将动态转化为静态处理,而且代码 ...

  8. BZOJ4237 JOISC2014 稻草人 CDQ分治、单调栈

    传送门 题意:给出平面上$N$个点,求满足以下两个条件的矩形:①左下角与右上角各有一个点:②矩形内部没有点.$N \leq 2 \times 10^5$,所有数字大于等于$0$,保证坐标两两不同 最开 ...

  9. AT1225 稻草人(cdq分治+二分)

    题目链接 Link 思路分析 题目要求我们统计二维平面内的点所构成的不含其他点的矩形个数,因此想到 cdqcdqcdq 分治. 我们先按照横坐标递增排序,这样就只用考虑左下角在 [l,mid][l,m ...

最新文章

  1. java 注解报错_java注解验证接收参数 返回注解字段的错误
  2. Mocha BSM应用管理——Lotus Domino监控与管理
  3. bootstranp选项卡怎么把每个选项卡里面的表单分开提交_EXCEL 宏应用基础知识,利用已实现的宏,制作自己的功能选项卡...
  4. [C++基金会]位计算 游戏开发中的应用
  5. iframe中跨域页面访问parent的方法
  6. 欢迎使用CSDN-markdown编辑器12213123
  7. 给1-3年的前端 6 点诚心建议
  8. 你羡慕了吗?10万个数字人民币红包派发,每个200元
  9. Bootstrap+DataTables后端排序分页详解
  10. C/C++ Memory Layout
  11. oracle应用程序开发,关于Oracle 数据库应用程序开发问题
  12. CentOS-6.4 安装 Memcached
  13. linux服务器知识学习:linux系统的目录结构
  14. Drool的global变量
  15. 蓝墨云班课php答案,蓝墨云班课试题库答案
  16. 数据结构-左倾红黑树
  17. SpringBoot整合Redis + SpringCache + Protobuf,优雅地实现key-value键值对存储DEMO。
  18. adb连接网易mumu模拟器
  19. RichFaces第一例
  20. kali 镜像下载(免费下载)

热门文章

  1. python爬虫什么意思-终于知道python爬虫是什么意思
  2. python入门指南by-Python 入门指南
  3. iOS语音识别功能实现
  4. Android基于讯飞语音SDK实现语音识别
  5. 启达传媒-微信小程序|微信小程序工具|微信小程序开发|微信小程序制作
  6. 怎么python编程excel_Python操作excel
  7. JavaScript-关于变量
  8. Redis--高并发之分布式锁
  9. 【Servlet笔记】Servlet入门
  10. 【linux】常用网络操作