PICTURE

题目描述

N(N<5000) 张矩形的海报,照片和其他同样形状的图片贴在墙上。它们的边都是垂直的或水平的。每个矩形可以部分或者全部覆盖其他矩形。所有的矩形组成的集合的轮廓称为周长。写一个程序计算周长。

图 1 是一个有 7 个矩形的例子:

图 1.一个 7 个矩形的集合对应的轮廓为图 2 所示的所有线段的集合:

图 2. 矩形集合的轮廓

所有矩形的顶点坐标均为整数。所有的坐标都在 [-10000,10000] 的范围内,并且任何一个矩形面积都为整数。结果的值可能需要 32 位有符号整数表示。

输入

第1行: N,张贴在墙上的矩形的数目。 第 2..N+1行 接下来的N行中,每行都有两个点的坐标,分别是矩形的左下角坐标和右上角坐标。每一个坐标由 X 坐标和 Y 坐标组成。

输出

只有一行,为一个非负整数,表示输入数据中所有矩形集合的轮廓长度。

样例输入

7
-15 0 5 10
-5 8 20 25
15 -4 24 14
0 -6 16 4
2 15 10 22
30 10 36 20
34 0 40 16

样例输出

228

自己写(chao)的,并没有用线段树维护,加了快读8ms
 #include <cstdio>
#include <algorithm>
#include <cstring>
using namespace std; struct data {
int lx, rx;
int ly, ry;
}; const int maxn = , maxx = ;
int n;
data a[maxn + ];
int level[maxx + ]; bool cmp_x(data x, data y) {
return x.lx < y.lx;
} bool cmp_y(data x, data y) {
return x.ly < y.ly;
} int in() {
int f = , p = ;
char c;
while (c < '' || c > '') {
c = getchar();
if (c == '-') {
f = -;
}
}
while (c >= '' && c <= '') {
p = p * + c - '';
c = getchar();
}
p *= f;
return p;
} void init() {
n = in();
for (int i = ; i <= n; i++) {
a[i].lx = in();
a[i].ly = in();
a[i].rx = in();
a[i].ry = in();
a[i].lx += ;
a[i].ly += ;
a[i].rx += ;
a[i].ry += ;
}
} int solve_x() {
memset(level, -, sizeof(level));
int ans = ;
sort(a + , a + + n, cmp_x);
for (int i = ; i <= n; i++) {
for (int j = a[i].ly; j < a[i].ry; j++) {
if (level[j] < a[i].lx) {
ans += ;
}
if (level[j] < a[i].rx) {
level[j] = a[i].rx;
}
}
}
return ans;
} int solve_y() {
memset(level, -, sizeof(level));
int ans = ;
sort(a + , a + + n, cmp_y);
for (int i = ; i <= n; i++) {
for (int j = a[i].lx; j < a[i].rx; j++) {
if (level[j] < a[i].ly) {
ans += ;
}
if (level[j] < a[i].ry) {
level[j] = a[i].ry;
}
}
}
return ans;
} int main() {
init();
printf("%d\n", solve_x() + solve_y());
return ;
}

下面是学长的QAQQ用了线段树维护

 #include<cstdio>
#include<algorithm>
#define MN 10000
#define MX 20000
#define L (k << 1)
#define R ((k << 1) + 1)
using namespace std; struct work{ //扫描线
int x, l, r, p;
}x[MN + ], y[MN + ]; bool cmp(work a, work b){
return a.x == b.x ? a.p > b.p : a.x < b.x;
} struct data{
int x, s;
}; data operator + (data a, data b){
if (a.x == b.x) {
return (data) {
a.x, a.s + b.s
};
}
return a.x < b.x ? a : b;
} struct node{
int l, r, mk;
data x;
}t[MX * + ]; inline void up (int k){
t[k].x = t[L].x + t[R].x;
} inline void add(int k, int x){
t[k].x.x += x;
t[k].mk += x;
} inline void down(int k){
if (t[k].mk) {
add(L, t[k].mk);
add(R, t[k].mk);
t[k].mk = ;
}
} void build(int k, int l, int r) {
t[k].l = l;
t[k].r = r;
if (l == r) {
t[k].x.s = ;
return;
}
int mid = l + r >> ;
build(L, l, mid);
build(R, mid + , r);
up(k);
} void renew(int k, int l, int r, int x) {
if (t[k].l == l && t[k].r == r) {
add(k, x);
return;
}
down(k);
int mid = t[k].l + t[k].r >> ;
if (r <= mid) {
renew(L, l, r, x);
}
else if (l > mid) {
renew(R, l, r, x);
}
else {
renew(L, l, mid, x);
renew(R, mid + , r, x);
}
up(k);
} data query(int k, int l, int r){
if (t[k].l == l && t[k].r == r) {
return t[k].x;
}
down(k);
int mid = (t[k].l + t[k].r) >> ;
if (r <= mid) {
return query(L, l, r);
}
if (l > mid) {
return query(R, l, r);
}
return query(L, l, mid) + query(R, mid + , r);
}
int n, ans;
void solve (work *x) {
for (int i = ; i < n; i++) {
if (x[i].p < ) {
renew(, x[i].l, x[i].r, -);
}
data d = query(, x[i].l, x[i].r);
if (x[i].p > ) {
renew(, x[i].l, x[i].r, );
}
ans += d.x ? : d.s;
}
} int main(){
int i, x0, y0, x1, y1;
scanf("%d", &n);
for (int i = ; i < n; ++i) {
scanf("%d%d%d%d", &x0, &y0, &x1, &y1);
x0 += MN;
y0 += MN;
x1 += MN;
y1 += MN;
x[i] = (work) {
y0, x0, x1 - ,
};
x[i + n] = (work) {
y1, x0, x1 - , -
};
y[i] = (work) {
x0, y0, y1 - ,
};
y[i + n] = (work) {
x1, y0, y1 - , -
};
}
n <<= ;
sort(x, x + n, cmp);
sort(y, y + n, cmp);
build(, , MX);
solve(x);
solve(y);
printf("%d", ans);
return ;
}
												

[线段树]picture的更多相关文章

  1. [矩形并-扫描线-线段树]Picture

    最近在补数学和几何,没啥好写的,因为已经决定每天至少写一篇了,今天随便拿个题水水. 题目大意:给你N个边平行于坐标轴的矩形,求它们并的周长.(N<=5000) 思路:这个数据范围瞎暴力就过了,但 ...

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

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

  3. 51nod 1206 Picture 矩形周长求并 | 线段树 扫描线

    51nod 1206 Picture 矩形周长求并 | 线段树 扫描线 #include <cstdio> #include <cmath> #include <cstr ...

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

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

  5. HDU 1828 / POJ 1177 Picture (线段树扫描线,求矩阵并的周长,经典题)

    做这道题之前,建议先做POJ 1151  Atlantis,经典的扫描线求矩阵的面积并 参考连接: http://www.cnblogs.com/scau20110726/archive/2013/0 ...

  6. 【IOI1998】Picture(扫描线+线段树)

    问题来源:IOI1998 D2T1 题意:就是在一个平面内给出n个矩形,叫你计算将这些矩形合并以后,新图形的周长. 例如: 上图是原本的矩形们 ---------->合并后的图形 解题思路:拿一 ...

  7. hdu 1828 Picture(线段树扫描线矩形周长并)

    线段树扫描线矩形周长并 #include <iostream> #include <cstdio> #include <algorithm> #include &l ...

  8. POJ 1177 Picture(线段树:扫描线求轮廓周长)

    题目链接:http://poj.org/problem?id=1177 题目大意:若干个矩形,求这些矩形重叠形成的图形的轮廓周长. 解题思路:这里引用一下大牛的思路:kuangbin 总体思路: 1. ...

  9. 【HDOJ1828&&POJ1177】Picture(线段树,扫描线)

    题意:给定n个矩形,求他们的并的周长 n<=5e3,abs(x[i])<=1e4 思路:From https://www.cnblogs.com/kuangbin/archive/2013 ...

随机推荐

  1. SPSS-生存分析

    生存分析 定义:一些医学事件所经历的时间:从开始观察到事件发生的时间,不是短期内可以明确判断的.针对这类生存资料的分析方法叫生存分析.生存分析的基本概念1.终点事件终点事件outcome event: ...

  2. 前端三大框架之一React入门教程

    相信大家对框架这个词都很熟悉吧,我一直喜欢js原生来开发,但是目前都要求工作效率,所有使用框架或者是库会使我们开发更加方便和快速,甚至一个人干十个人的活.. 框架优点: 1.方便开发.快速写功能 2. ...

  3. Xshell 连接ubuntu虚拟机失败解决办法

    当我们在VMWare上安装好Ubuntu虚拟机后,有时候会需要使用多个terminal窗口,但是在虚拟机中多个窗口互相切换查看不方便,这时候用物理机的xshell工具连接到虚拟机中去就显得很方便.直接 ...

  4. mysql 在登陆的时候出现error 1045 (28000): 错误解决办法

    错误显示:ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: YES) 解决方案: 1.找到配 ...

  5. BOM 表

    ';--查看BOM创建日期时间 SELECT * FROM SAPSR3.ZSTPO_OUT2011_1@SAP_SEP; SELECT * FROM SAPSR3.ZSTPO_OUT2012_1@S ...

  6. Linq to sql 之 ExecuteQuery 错误:指定的转换无效

    问题:通过dbContext.ExecuteQuery 得到数据并赋值给一个集合. 代码: public IEnumerable<LeaveCodeSum> GetLeavTotal(st ...

  7. java定义object数组(可以存储String或int等多种类型)

    需求| 想在数组中既有String类型又有int等类型,所以需要定义数组为Object类型   背景| 现在有一个字符串params,需要对其进行逗号分隔赋值到数组里,这时遇到了个问题,即使直接定义的 ...

  8. Appium1.6,安装WebDriverAgent(WDA)

    前提说明:Appium1.6通过WebDriverAgent来操作iOS,所以需要在Appium下安装一份WebDriverAgent,并且将程序安装到iOS真机上 (如果是模拟器不需要这步骤)   ...

  9. char和varchar查询速度、存储空间比较详解(转)

    转:http://tech.diannaodian.com/dw/data/sql/2011/1005/135572.html 一.数据行结构 1.char(n): 系统分配n个字节给此字段,不管字段 ...

  10. NumPy 从已有的数组创建数组

    NumPy 从已有的数组创建数组 本章节我们将学习如何从已有的数组创建数组. numpy.asarray numpy.asarray 类似 numpy.array,但 numpy.asarray 只有 ...