1542

1255

两道扫描线+线段树的入门题。

基本没有什么区别,前者是模板,后者因为是求覆盖次数至少在两次以上的,这个同样是具有并集性质的,所以把cover的判断条件更改一下就可以了qwq。

hdu1542 代码如下:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 200010
using namespace std;
int n,c,cnt;
double y[MAXN];
struct Node{
double x,l,r;
int cover;
bool flag;
}node[MAXN];
struct Line
{
double x,y_up,y_down;
int flag;
}line[MAXN];
inline bool cmp(struct Line x,struct Line y){return x.x<y.x;}
inline int ls(int x){return x<<1;}
inline int rs(int x){return x<<1|1;}
inline void build(int x,int l,int r)
{
node[x].l=y[l],node[x].r=y[r],node[x].x=-1,node[x].flag=false,node[x].cover=0;
if(l+1==r){node[x].flag=true; return;}
int mid=(l+r)>>1;
build(ls(x),l,mid);
build(rs(x),mid,r);
}
inline double q_update(int x,double pos,double l,double r,int flag)
{
if(l>=node[x].r||r<=node[x].l) return 0;
if(node[x].flag)
{
if(node[x].cover<=0)
{
node[x].x=pos;
node[x].cover+=flag;
return 0;
}
double pre=node[x].x;
double ans=(pos-pre)*(node[x].r-node[x].l);
node[x].x=pos;
node[x].cover+=flag;
return ans;
}
return q_update(ls(x),pos,l,r,flag)+q_update(rs(x),pos,l,r,flag);
}
int main()
{
scanf("%d",&n);
while(n!=0)
{
double x1,x2,y1,y2;
cnt=0;
for(int i=1;i<=n;i++)
{
scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
line[++cnt].x=x1,line[cnt].y_down=y1,line[cnt].y_up=y2,line[cnt].flag=1,y[cnt]=y1;
line[++cnt].x=x2,line[cnt].y_down=y1,line[cnt].y_up=y2,line[cnt].flag=-1,y[cnt]=y2;
}
sort(&line[1],&line[cnt+1],cmp);
sort(&y[1],&y[cnt+1]);
build(1,1,cnt);
double ans=0;
for(int i=1;i<=cnt;i++)
ans+=q_update(1,line[i].x,line[i].y_down,line[i].y_up,line[i].flag);
printf("Test case #%d\nTotal explored area: %.2lf\n\n",++c,ans);
scanf("%d",&n);
}
return 0;
}

hdu1255 代码如下:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 200010
using namespace std;
int n,c,cnt,t;
double y[MAXN];
struct Node{
double x,l,r;
int cover;
bool flag;
}node[MAXN];
struct Line
{
double x,y_up,y_down;
int flag;
}line[MAXN];
inline bool cmp(struct Line x,struct Line y){return x.x<y.x;}
inline int ls(int x){return x<<1;}
inline int rs(int x){return x<<1|1;}
inline void build(int x,int l,int r)
{
node[x].l=y[l],node[x].r=y[r],node[x].x=-1,node[x].flag=false,node[x].cover=0;
if(l+1==r){node[x].flag=true; return;}
int mid=(l+r)>>1;
build(ls(x),l,mid);
build(rs(x),mid,r);
}
inline double q_update(int x,double pos,double l,double r,int flag)
{
if(l>=node[x].r||r<=node[x].l) return 0;
if(node[x].flag)
{
if(node[x].cover<=1)
{
node[x].x=pos;
node[x].cover+=flag;
return 0;
}
double pre=node[x].x;
double ans=(pos-pre)*(node[x].r-node[x].l);
node[x].x=pos;
node[x].cover+=flag;
return ans;
}
return q_update(ls(x),pos,l,r,flag)+q_update(rs(x),pos,l,r,flag);
}
int main()
{
scanf("%d",&t);
while(t--)
{
scanf("%d",&n);
double x1,x2,y1,y2;
cnt=0;
for(int i=1;i<=n;i++)
{
scanf("%lf%lf%lf%lf",&x1,&y1,&x2,&y2);
line[++cnt].x=x1,line[cnt].y_down=y1,line[cnt].y_up=y2,line[cnt].flag=1,y[cnt]=y1;
line[++cnt].x=x2,line[cnt].y_down=y1,line[cnt].y_up=y2,line[cnt].flag=-1,y[cnt]=y2;
}
sort(&line[1],&line[cnt+1],cmp);
sort(&y[1],&y[cnt+1]);
build(1,1,cnt);
double ans=0;
for(int i=1;i<=cnt;i++)
ans+=q_update(1,line[i].x,line[i].y_down,line[i].y_up,line[i].flag);
printf("%.2lf\n",ans);
}
return 0;
}

hdu 1542/1255 Atlantis/覆盖的面积的更多相关文章

  1. 【 HDU 1255】 覆盖的面积(矩阵面积交,线段树,扫描法)

    [题目] 覆盖的面积 Problem Description 给定平面上若干矩形,求出被这些矩形覆盖过至少两次的区域的面积. Input 输入数据的第一行是一个正整数T(1<=T<=100 ...

  2. 【HDU 1542】Atlantis 矩形面积并(线段树,扫描法)

    [题目] Atlantis Problem Description There are several ancient Greek texts that contain descriptions of ...

  3. 【HDU 1542】Atlantis(线段树+离散化,矩形面积并)

    求矩形面积并,离散化加线段树. 扫描线法: 用平行x轴的直线扫,每次ans+=(下一个高度-当前高度)*当前覆盖的宽度. #include<algorithm> #include<c ...

  4. HDU 1542:Atlantis(扫描线+线段树 矩形面积并)***

    题目链接 题意 给出n个矩形,求面积并. 思路 使用扫描线,我这里离散化y轴,按照x坐标从左往右扫过去.离散化后的y轴可以用线段树维护整个y上面的线段总长度,当碰到扫描线的时候,就可以统计面积.这里要 ...

  5. 【42.49%】【hdu 1542】Atlantis(线段树扫描线简析)

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

  6. 线段树扫描线(一、Atlantis HDU - 1542(覆盖面积) 二、覆盖的面积 HDU - 1255(重叠两次的面积))

    扫描线求周长: hdu1828 Picture(线段树+扫描线+矩形周长) 参考链接:https://blog.csdn.net/konghhhhh/java/article/details/7823 ...

  7. (HDU 1542) Atlantis 矩形面积并——扫描线

    n个矩形,可以重叠,求面积并. n<=100: 暴力模拟扫描线.模拟赛大水题.(n^2) 甚至网上一种“分块”:分成n^2块,每一块看是否属于一个矩形. 甚至这个题就可以这么做. n<=1 ...

  8. HDU 1255 覆盖的面积(线段树:扫描线求面积并)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1255 题目大意:给你若干个矩形,让你求这些矩形重叠两次及以上的部分的面积. 解题思路:模板题,跟HDU ...

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

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

随机推荐

  1. PHP - 输出缓存 - 关于ob系列函数和flush函数

    偶然机会看到了flush().知道他的神奇功能可以用在异步传输的comet 模式之后,于是我去试了试这个方法.然后翻手册去看了看什么意思.发现它神奇的和ob类函数在一起.有点好奇,先放一放,来说flu ...

  2. Excel 数字处理

    说明 最近在做一个比较小型的网站,需要批量导入注册用户.用户的信息写在一张excel表格里面. 所以就需要读取excel.所以就记录下遇到的问题,以及以后查看. 相关技术 使用的POI解析Excel需 ...

  3. 【原】Coursera—Andrew Ng机器学习—课程笔记 Lecture 17—Large Scale Machine Learning 大规模机器学习

    Lecture17 Large Scale Machine Learning大规模机器学习 17.1 大型数据集的学习 Learning With Large Datasets 如果有一个低方差的模型 ...

  4. Makefile里面打印信息

    Makefile的规则相对来说还是比较复杂的,上手不容易,没有系统研究过,往往搞不清楚状况.如果掌握了基本的调试手段,那对我们写出正确的Makefile会非常有帮助.而在Makefile中,最重要的调 ...

  5. 在ios端点击按钮闪烁解决方法(小tips)

    在ios端,safari浏览器上触发click事件有300ms的延迟响应,为touch添加的样式会和click冲突而出现闪烁问题 在safari中触摸事件的相应顺序如下: touchstart --& ...

  6. poj2796 Feel good

    题目给出N个数,找出一段区间使得区间最小值乘区间和的值最大 其中N<=100000 分析: 单调队列(单调栈) 求出每个值作为最小值时最长的影响区间,然后枚举判断 这找出最长影响区间应该算是单调 ...

  7. Java方法重写与super关键字

    ----------siwuxie095                     方法的重写:     (1)在继承中也存在着重写的概念,其实就是子类定义了和父类同名的方法     (2)定义:方法名 ...

  8. iOS倒计时

    现在开发基本上都有发送验证码,倒计时,下面说一种 #import <UIKit/UIKit.h> @interface UIButton (CountDown) -(void)startT ...

  9. ios加载本地html

    UIWebView加载工程本地网页与本地图片 - (void)viewDidLoad { [super viewDidLoad]; NSString *filePath = [[NSBundle ma ...

  10. KVM下raw和qcow2格式磁盘文件IO测试

    1. Host OS 环境 CPU: Intel Xeon E5620 2.40GHz MEM: 16GB DISK: 500GB SATA OS: CentOS5.7 64bit 2. Guest ...