Atlantis poj1151 线段树扫描线

题意

题目给了n个矩形,每个矩形给了左下角右上角的坐标,矩形可能会重叠,求的是矩形最后的面积。

题解思路

这个是我线段树扫描线的第一题,听了学长的讲解,仔细研读了学长的代码,也算初步入门。

这里我们竖着的扫描线,从左到右来进行扫描的。

线段树这里端点代表的是一个区间

这里的y范围比较大,所以咱们需要离散化。

代码实现

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<map>
#define mid ((tre[rt].l+tre[rt].r)>>1)
#define ls (rt<<1)
#define rs (rt<<1|1)
using namespace std;
const int maxn=1e2+7;
struct node{ //四元组
double x, y1, y2;
int k; //左边的边k是1, 右边的k为-1
bool friend operator < (node a, node b)
{
return a.x < b.x;
}
}a[maxn<<1]; struct tree{
int l, r, cnt; //cnt记录区间被标记的次数
double len;
}tre[maxn<<3]; map<double, int> mp;
double raw[maxn<<1];
int n,num; void build(int rt, int l, int r)
{
tre[rt].l=l;
tre[rt].r=r;
tre[rt].len=tre[rt].cnt=0;
if(l==r) return ;
build(ls, l, mid);
build(rs, mid+1, r);
} void change(int rt, int l, int r, int k)
{
if(l <= tre[rt].l && tre[rt].r <= r)
{
tre[rt].cnt+=k;
if(tre[rt].cnt>0)
{
tre[rt].len=raw[tre[rt].r+1] - raw[tre[rt].l];
}
else if(tre[rt].l==tre[rt].r) //到达端点了
{
tre[rt].len=0;
}
else tre[rt].len=tre[ls].len+tre[rs].len; return ;
}
if(l <= mid) change(ls, l, r, k);
if(r > mid) change(rs, l, r, k);
tre[rt].len = tre[rt].cnt > 0 ? raw[tre[rt].r+1] - raw[tre[rt].l] : tre[ls].len+tre[rs].len;
} int main()
{
while(scanf("%d", &n) && n)
{
int cnt;
double x1, y1, x2, y2;
for(int i=1; i<=n; i++)
{
cnt=i<<1;
scanf("%lf%lf%lf%lf", &x1, &y1, &x2, &y2);
a[cnt-1].x=x1; a[cnt-1].y1=y1; a[cnt-1].y2=y2; a[cnt-1].k=1;
a[cnt].x=x2; a[cnt].y1=y1; a[cnt].y2=y2; a[cnt].k=-1;
raw[cnt-1]=y1; raw[cnt]=y2;
}
n<<=1;
sort(raw+1, raw+1+n);
int m=unique(raw+1, raw+n+1)-(raw+1);
for(int i=1; i<=m; i++)
{
mp[raw[i]]=i;
}
sort(a+1, a+n+1);
build(1, 1, m-1); //这里线段树的点记录的区域,因为有m个y,所以就相当于m-1个区域
double ans=0;
for(int i=1; i<n; i++) //只需要处理到倒数第二个点即可
{
int l=mp[a[i].y1], r=mp[a[i].y2]-1;
change(1, l, r, a[i].k);
ans += tre[1].len*(a[i+1].x - a[i].x);
}
printf("Test case #%d\nTotal explored area: %.2f\n\n", ++num, ans);
}
return 0;
}

Atlantis poj1151 线段树扫描线的更多相关文章

  1. hdu1542 Atlantis (线段树+扫描线+离散化)

    Atlantis Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total S ...

  2. POJ1151+线段树+扫描线

    /* 线段树+扫描线+离散化 求多个矩形的面积 */ #include<stdio.h> #include<string.h> #include<stdlib.h> ...

  3. poj1151 Atlantis (线段树+扫描线+离散化)

    有点难,扫描线易懂,离散化然后线段树处理有点不太好理解. 因为这里是一个区间,所有在线段树中更新时,必须是一个长度大于1的区间才是有效的,比如[l,l]这是一根线段,而不是区间了. AC代码 #inc ...

  4. P - Atlantis (线段树+扫描线)

      There are several ancient Greek texts that contain descriptions of the fabled island Atlantis. Som ...

  5. HDU 1542 Atlantis(线段树扫描线+离散化求面积的并)

    Atlantis Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total S ...

  6. Atlantis(POJ1151+线段树+扫描线)

    题目链接:http://poj.org/problem?id=1151 题目: 题意:求所有矩形的面积,重合部分只算一次. 思路:扫描线入门题,推荐几篇学扫描线的博客: 1.http://www.cn ...

  7. HDU 1542"Atlantis"(线段树+扫描线求矩形面积并)

    传送门 •题意 给你 n 矩形,每个矩形给出你 $(x_1,y_1),(x_2,y_2)$ 分别表示这个矩形的左下角和右上角坐标: 让你求这 n 个矩形并的面积: 其中 $x \leq 10^{5} ...

  8. POJ 1151 Atlantis(线段树-扫描线,矩形面积并)

    题目链接:http://poj.org/problem?id=1151 题目大意:坐标轴上给你n个矩形, 问这n个矩形覆盖的面积 题目思路:矩形面积并. 代码如下: #include<stdio ...

  9. 【POJ1151】Atlantis(线段树,扫描线)

    [POJ1151]Atlantis(线段树,扫描线) 题面 Vjudge 题解 学一学扫描线 其实很简单啦 这道题目要求的就是若干矩形的面积和 把扫描线平行于某个轴扫过去(我选的平行\(y\)轴扫) ...

随机推荐

  1. Python---进阶---函数式编程---lambda

    一. 利用map()函数,把用户输入的不规范的英文,变成首字母大写,其他小写的规范的名字:比如说["ADMAm", "LISA", "JACK&quo ...

  2. Java语言Lang包下常用的工具类介绍_java - JAVA

    文章来源:嗨学网 敏而好学论坛www.piaodoo.com 欢迎大家相互学习 无论你在开发哪中 Java 应用程序,都免不了要写很多工具类/工具函数.你可知道,有很多现成的工具类可用,并且代码质量都 ...

  3. [CF1004E] Sonya and Ice-cream

    问题描述 Sonya likes ice cream very much. She eats it even during programming competitions. That is why ...

  4. STM32内部时钟设置-寄存器版

    STM32寄存器版本——内部时钟设置 同时要记得把延时初始化函数设置好 //系统时钟初始化函数 //pll:选择的倍频数,从2开始,最大值为16 //pll:选择的倍频数,这里使用内部时钟,PLL为4 ...

  5. jQuery 遍历 - 同胞(siblings)

    同胞拥有相同的父元素. 通过 jQuery,您能够在 DOM 树中遍历元素的同胞元素. 在 DOM 树中水平遍历 有许多有用的方法让我们在 DOM 树进行水平遍历: siblings() next() ...

  6. Java——常用类(Enum)

    [枚举类型]  <1>只能取特定值中的一个.  <2>使用enum关键字.  <3>是java.lang.Enum类型.   [程序分析]    public en ...

  7. CSS的一些单位,如rem、px、em、vw、vh、vm

    总结了一下一些单位的不同 px:像素(pixel)相对长度单位,,是相对于屏幕显示器分辨率而言的: em:em的值并不是固定的,会集成父级元素的字体大小: 注意: 1.body选择其中声明Font-s ...

  8. [CSP-S模拟测试]:超级树(DP)

    题目传送门(内部题5) 输入格式 一行两个整数$k$.$mod$,意义见上. 输出格式 一行一个整数,代表答案. 样例 样例输入1: 2 100 样例输出1: 样例输入2: 3 1000 样例输出2: ...

  9. Java解析JSON文件的方法

    http://blog.sina.com.cn/s/blog_628cc2b70101dydc.html java读取文件的方法 http://www.cnblogs.com/lovebread/ar ...

  10. ubuntu18.04设置静态IP

    ubuntu18与ubuntu14.16设置静态ip地方方法不同,很多人没去读更新文档的时候往往会设置静态ip地址不成功,下面是具体的设置方法 做之前一定要确认自己操作系统的版本,每个版本设置的方法有 ...