线段树扫描线矩形周长并

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>
#define MAXN 22222
using namespace std; int len[MAXN<<2];
bool lbd[MAXN<<2],rbd[MAXN<<2];
int numseg[MAXN<<2];
int cnt[MAXN<<2]; struct line
{
int s,e,h,type; }L[MAXN]; bool cmp(line a,line b)
{
if(a.h==b.h)return a.type>b.type;
return a.h<b.h;
} void pushup(int num,int l,int r)
{
if(cnt[num])//全部覆盖
{
lbd[num]=rbd[num]=1;
len[num]=r-l+1;
numseg[num]=2;
}
else if(l==r)//没有完全覆盖 且L==R 不就意味着没有东西在它上面么
{
lbd[num]=rbd[num]=numseg[num]=len[num]=0;
}
else
{
lbd[num]=lbd[num<<1];
rbd[num]=rbd[num<<1|1];
len[num]=len[num<<1]+len[num<<1|1];
numseg[num]=numseg[num<<1] + numseg[num<<1|1];
if(rbd[num<<1] && lbd[num<<1|1])numseg[num]-=2;//重合
}
} void update(int num,int s,int e,int l,int r,int val)
{
if(l<=s && r>=e)
{
cnt[num]+=val;
pushup(num,s,e);
return;
}
int mid=(s+e)>>1; if(l<=mid)update(num<<1,s,mid,l,r,val);
if(r>mid)update(num<<1|1,mid+1,e,l,r,val);
pushup(num,s,e);
} int main()
{
int n;
while(scanf("%d",&n)!=EOF)
{
int lmost=10000,rmost=-10000;
int m=0;
for(int i=1;i<=n;i++)
{
int a,b,c,d;
scanf("%d%d%d%d",&a,&b,&c,&d);
lmost=min(lmost,a);
rmost=max(rmost,c);
L[m].s=a;L[m].e=c;L[m].h=b;L[m++].type=1;
L[m].s=a;L[m].e=c;L[m].h=d;L[m++].type=-1;
}
sort(L,L+m,cmp);
int ans=0;
int last=0;//记录更新之前的X周的覆盖区域
for(int i=0;i<m;i++)
{
if(L[i].s<L[i].e)update(1,lmost,rmost-1,L[i].s,L[i].e-1,L[i].type);
ans+=numseg[1]*(L[i+1].h-L[i].h);//计算竖直方向的长度
ans+=abs(len[1]-last);
last = len[1];
}
printf("%d\n",ans);
}
}

hdu 1828 Picture(线段树扫描线矩形周长并)的更多相关文章

  1. hdu1828 Picture(线段树+扫描线+矩形周长)

    看这篇博客前可以看一下扫描线求面积:线段树扫描线(一.Atlantis HDU - 1542(覆盖面积) 二.覆盖的面积 HDU - 1255(重叠两次的面积))  解法一·:两次扫描线 如图我们可以 ...

  2. HDU 1828 Picture (线段树+扫描线)(周长并)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1828 给你n个矩形,让你求出总的周长. 类似面积并,面积并是扫描一次,周长并是扫描了两次,x轴一次,y ...

  3. HDU 1828 Picture (线段树:扫描线周长)

    依然是扫描线,只不过是求所有矩形覆盖之后形成的图形的周长. 容易发现,扫描线中的某一条横边对答案的贡献. 其实就是 加上/去掉这条边之前的答案 和 加上/去掉这条边之后的答案 之差的绝对值 然后横着竖 ...

  4. POJ 1177/HDU 1828 picture 线段树+离散化+扫描线 轮廓周长计算

    求n个图矩形放下来,有的重合有些重合一部分有些没重合,求最后总的不规则图型的轮廓长度. 我的做法是对x进行一遍扫描线,再对y做一遍同样的扫描线,相加即可.因为最后的轮廓必定是由不重合的线段长度组成的, ...

  5. HDU 1828 / POJ 1177 Picture --线段树求矩形周长并

    题意:给n个矩形,求矩形周长并 解法:跟求矩形面积并差不多,不过线段树节点记录的为: len: 此区间线段长度 cover: 此区间是否被整个覆盖 lmark,rmark: 此区间左右端点是否被覆盖 ...

  6. hdu 1828 Picture(线段树 || 普通hash标记)

    http://acm.hdu.edu.cn/showproblem.php?pid=1828 Picture Time Limit: 6000/2000 MS (Java/Others)    Mem ...

  7. hdu 1828 Picture(线段树轮廓线)

    Picture Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Sub ...

  8. HDU 1264 Counting Squares (线段树-扫描线-矩形面积并)

    版权声明:欢迎关注我的博客.本文为博主[炒饭君]原创文章,未经博主同意不得转载 https://blog.csdn.net/a1061747415/article/details/25471349 P ...

  9. HDU 1542 - Atlantis - [线段树+扫描线]

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1542 Time Limit: 2000/1000 MS (Java/Others) Memory Li ...

随机推荐

  1. 转:前端页面a标签嵌套a标签效果的两种解决方案

      这是由工作中的一个小改动需求得到的这个解决方案的:那个需求是这样的,如图: 需求原来是球队名字没有点击功能的,而蓝色方框两队之间的比赛点击的时候会跳转到比赛文字直播页面.现在需要要求点击球队名字要 ...

  2. php-fpm 配置文件检测

    用过 Nginx 的兄弟都知道,修改 Nginx 配置文件之后,可以使用 nginx -t 来检测配置文件是否有语法错误. 今天配置 opcache 的时候,发现 php-fpm 也可以检测 php- ...

  3. python全栈开发day49-jquery的位置信息、事件流、事件对象,事件委托,事件绑定和解绑

    一.昨日内容回顾    1. jQuery的属性操作 1) html属性操作:attr 2) DOM属性操作:prop 3) 类样式操作:addClass.removeClass.toggleClas ...

  4. Python 2维数组90度旋转

    一.二维列表 a = [[col for col in range(4)] for row in range(4)] [[0, 1, 2, 3], [0, 1, 2, 3], [0, 1, 2, 3] ...

  5. Free DIY Tour HDU1224

    一道很好的dfs加储存路径的题目  :路径保存:每次dfs都存i 当大于max时 将临时数组保存到答案数组 并不是当 当前值大于最大值时更新路径 还要加上一个条件:能回去 #include<bi ...

  6. 【Java】 剑指offer(34) 二叉树中和为某一值的路径

    本文参考自<剑指offer>一书,代码采用Java语言. 更多:<剑指Offer>Java实现合集   题目 输入一棵二叉树和一个整数,打印出二叉树中结点值的和为输入整数的所有 ...

  7. moodle 笔记

    默认版块的设置: //这些变量为新课程定义了DEFAULT块变量如果设置了这个变量,它将覆盖所有其他变量,并且是唯一使用的变量s $CFG->defaultblocks_override = ' ...

  8. Volley网络通信框架

    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools=&q ...

  9. 使用SQL逆向生成PDM文件

    首先导出表结构,可以使用Navicat 或者DataGrip 生成SQL文件后使用PowerDesigner 指定数据库类型,选择SQL文件即可

  10. 聊聊ReentrantLock的内部实现

    大家都用过ReentrantLock,但是大家对内部实现是否足够了解呢,下面我就简单说一下其中的实现原理. ReentrantLock是可重入锁,也就是同一个线程可以多次获取锁,每获取一次就会进行一次 ...