线段切割&&矩形切割
来源:互联网 发布:mac查看硬盘使用情况 编辑:程序博客网 时间:2024/04/29 02:06
【参考BOLG】http://blog.csdn.net/acdreamers/article/details/8778225
【解释】直接沿用acdreamers大神的解释啦。
【题目】http://poj.org/problem?id=2528
【解题方法】线段树写过了,不说,这里学习另外一种代码量非常少的方法,线段切割。
利用线段切割,由于后贴的海报可能会覆盖前面的,而很明显知道前面的海报不会影响后面海报的可见性,所以应该从后面往
前面推。
所以程序中就有:for(i=n-1;i>=0;i--)
现在我们暂时只分析前一张海报与后一张海报的关系就可以了,然后递推就可以了。
我们用海报的长度来表示可见性,如果长度大于0,当然就可见啊
对于海报之间的关系,只有那么几种情况,但是看程序中只有3种关系,实际上在统计可见性时我们说只需要3种就够了,为什
么呢?
我们可以自己模拟一下:
如果两张海报没有交集,那么下面的那张海报一定是可见的,所以长度当然大于0,
如果两张海报有交集,就必然有4种关系,但是这里我们相当于只有两种就够了,就是后面的覆盖前面的右半部分,或者后面的
覆盖前面的左半部分,注意我们开始memset所有的海报长度是0,所以如果出现后面的海报全部覆盖前面的海报的情况就不用
管,因为它就是0,但是还有一种关系,就是后面的海报覆盖前面海报的中间部分,这样的话我们就可以把它当成覆盖左边部分
或者覆盖右边部分,因为我们的判断语句是
if(l<node[k].x)
if(r>node[k].y)
很明显可以看出实际上这两个语句包含了3种情况。而不仅仅代表只覆盖右部分或者左部分。
这样我们在结构体里面用ans统计每张海报最终的长度,实际上不一定是真正的长度哈,比如后一张只覆盖前一张的和中间部分
的那一种情况,实际上ans就只记录了前面的海报的左边部分,所以这样本题就解决了,线段切割实现起来更容易。
注意线段切割与矩形切割适用的范围:对边界范围大,操作数少的题目,我们选择矩形切割或者线段切割。
自己试了一些例子,没找出这种切割方法有什么漏洞,orzz!
【期望复杂度】O(nlogn)
【AC 代码】
//225msAC 代码 期望复杂度:nlogn#include <cstdio>#include <cstring>#include <iostream>#include <algorithm>using namespace std;const int maxn = 10005;struct node{ int x,y; int ans;}a[maxn];int n;void Cover(int l,int r,int k,int c){ while(k<n&&(r<a[k].x||l>a[k].y)) k++; if(k>=n){//当前进行切割的线段并没有和后面的线段相交 a[c].ans+=(r-l+1); return ; } if(l<a[k].x) Cover(l,a[k].x-1,k+1,c);//当前线段的右边被覆盖 if(r>a[k].y) Cover(a[k].y+1,r,k+1,c);//当前线段的左边被覆盖}int main(){ int T,sum; scanf("%d",&T); while(T--) { sum=0; memset(a,0,sizeof(a)); scanf("%d",&n); for(int i=0; i<n; i++) scanf("%d%d",&a[i].x,&a[i].y); for(int i=n-1; i>=0; i--){//这里是用后面的海报覆盖前面的海报,所以要从后面开始进行插入(进行线段切割); Cover(a[i].x,a[i].y,i+1,i); } for(int i=0; i<n; i++){ if(a[i].ans) sum++; } printf("%d\n",sum); } return 0;}
- 线段切割&&矩形切割
- 矩形切割
- 矩形切割
- 线段树思想实现矩形切割
- POJ 1151 Atlantis 矩形切割 || 线段树 扫描线
- 【COGS】950 切割矩形 线段树&树状数组
- [USACO3.1.4] 形成的区域 - 线段树/矩形切割
- 【矩形切割】卫星覆盖
- 【矩形切割】Atlantis
- POJ3277(矩形切割)
- HDU3634(矩形切割)
- POJ 1151 矩形切割
- [POJ1151] Atlantis - 矩形切割
- [codevs3235] 战争 - 矩形切割
- poj 2528 线段覆盖 求能看到的线段有几段 (线段切割) poj 3277 (矩形切割)
- POJ1151(矩形切割入门题)
- POJ3695(矩形切割中等题)
- sgu 177 Square 矩形切割
- UVA 11077 Find the Permutations(置换+dp)
- Ubuntu下解压文件
- static_cast, dynamic_cast, const_cast探讨
- qt超强精美绘图控件 - QCustomPlot一览 及 安装使用教程
- Java程序猿之IO(25)
- 线段切割&&矩形切割
- 计算机英语词汇总结
- 1050. 螺旋矩阵(25)
- 细思恐极----美国掌握网络世界生杀大权
- Swift基础之闭包Closure学习
- Linux简介
- ADB 常用指令
- 多线程六------从任务中产生返回值-Callable接口
- leetcode Longest Substring with At Most K Distinct Characters