UESTC_秋实大哥与家 2015 UESTC Training for Data Structures<Problem E>
E - 秋实大哥与家
Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others)
秋实大哥是一个顾家的男人,他认为人生就是旅途,不管我们漂到哪,最终还是会回到温暖的地方——家。
所以他买了很多家具。
秋实大哥的家可以看成一个W×H的矩阵,每一件家具可以看成一个矩形,他们放置在秋实大哥的家里,相互之间没有重叠。
现在秋实大哥购置了一个新的大小为1×M的家具,秋实大哥想知道他有多少种方式来安放这个家具。
Input
第一行包含四个整数W,H,n,M,表示秋实大哥家的大小为W×H,现在已有n个家具,新购置的家具大小为1×M。
接下来n行,每行包含4个整数x1,y1,x2,y2,分别表示这个家具左下角的坐标和右上角的坐标。
1≤n,H,W,M≤100000,1≤x1≤x2≤W,1≤y1≤y2≤H。
Output
输出一行包含一个整数,表示有多少种方案可以来放置秋实大哥的新家具,要求不能跟原有的家具重叠,也不能超出家的范围。
Sample input and output
| Sample Input | Sample Output |
|---|---|
3 3 1 2 |
8 |
解题报告:
注意到所有的家具是1 x m的,不外乎横放与竖放,我们先考虑横放,对于每个矩形,其左端线坐标为x1,右端线坐标为x2.
那么下列这些点肯定无法放置的(以这些点为最左端放置)
(X1-m+1,x2) , y ∈ [y1,y2]
那么问题就好解决了,每读入一个矩形,将其线延长,之后算不合法的面积,用总面积减去不合法的面积即为方案数.
竖放的道理一样,这里不再阐述.注意到 m = 1的情况,横 / 竖是一样的
#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
typedef long long ll;
using namespace std;
const int maxn = 6e5 + ;
const int maxtreesize = 6e5 + ;
int w,h,n,m,size=; typedef struct node
{
int l,r,cover,sum;
}; node tree[maxtreesize]; void push_up(int cur)
{
int lc = *cur;
int rc = *cur+;
if (tree[cur].cover)
tree[cur].sum = tree[cur].r - tree[cur].l;
else if(tree[cur].l == tree[cur].r ) // 叶子
tree[cur].sum = ;
else
{
if (tree[lc].cover && tree[rc].cover ) // Updata Father
tree[cur].sum = tree[lc].sum + tree[rc].sum;
else
tree[cur].sum = tree[lc].sum + tree[rc].sum;
} } void updata(int ql,int qr,int v,int cur)
{
int lc = *cur , rc = *cur + , l = tree[cur].l , r = tree[cur].r;
if (r == l) // 元
return;
if (l >= ql && r <= qr)
{
tree[cur].cover += v;
push_up(cur);
}
else
{
int mid = l + (r-l)/;
if (mid > ql)
updata(ql,qr,v,lc);
if (mid < qr)
updata(ql,qr,v,rc);
push_up(cur);
}
} void build_tree(int cur,int l,int r)
{
tree[cur].l = l,tree[cur].r = r;
if (r - l > )
{
int mid = l + (r-l)/;
build_tree(*cur,l,mid);
build_tree(*cur+,mid,r);
}
} typedef struct line
{
int x1,x2,y1,y2;
bool flag; // 0 是入边,1 是出边
inline int getx()
{
if (flag)
return x2;
else
return x1;
}
inline int gety()
{
if (flag)
return y2;
else
return y1;
}
}; line a[maxn]; // x 方向上被限制
line b[maxn]; // y 方向上被限制 bool cmp1(line a,line b)
{
return a.getx() < b.getx();
} bool cmp2(line a,line b)
{
return a.gety() < b.gety();
} void dump__()
{
for(int i = ; i < size ; ++ i)
{
if (a[i].flag == )
{
printf("入边 , x is %d , y1 is %d, y2 is %d\n",a[i].getx(),a[i].y1 , a[i].y2);
}
else
printf("出边 , x is %d , y1 is %d, y2 is %d\n",a[i].getx(),a[i].y1 , a[i].y2);
}
} void dump()
{
for(int i = ; i < size ; ++ i)
{
if (b[i].flag == )
{
printf("入边 , y is %d ,left is %d,right is %d\n",b[i].y1,b[i].x1,b[i].x2 );
}
else
{
printf("出边 , y is %d ,left is %d,right is %d\n",b[i].y2,b[i].x1,b[i].x2 );
}
}
} ll sall; //总面积 ll slove1()
{
ll res = ;
sort(a,a+size,cmp1);
int cur = ;
updata(a[].y1,a[].y2,,);
while(cur < size)
{
int dis = a[cur].getx() - a[cur-].getx();
res += (ll)dis*(ll)tree[].sum;
if (a[cur].flag & ) //出边
updata(a[cur].y1,a[cur].y2,-,);
else
updata(a[cur].y1,a[cur].y2,,);
cur++;
}
return sall - res;
} ll slove2()
{
ll res = ;
sort(b,b+size,cmp2);
int cur = ;
updata(b[].x1,b[].x2,,);
while(cur < size)
{
int dis = b[cur].gety() - b[cur-].gety();
res += (ll)dis*(ll)tree[].sum;
if (b[cur].flag & ) //出边
updata(b[cur].x1,b[cur].x2,-,);
else
updata(b[cur].x1,b[cur].x2,,);
cur++;
}
return sall - res;
} int main(int argc,char *argv[])
{
scanf("%d%d%d%d",&w,&h,&n,&m);
memset(tree,,sizeof(tree));
memset(a,,sizeof(a));
memset(b,,sizeof(b));
build_tree(,,max(w,h)+); // Build Tree
sall = (ll)w*(ll)h;
for(int i = ; i < n ; ++ i)
{
int x1,y1,x2,y2,oriy1,orix1;
scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
x1 -- , y1 -- ; //转换为线段式
orix1 = x1,oriy1 = y1;
x1 = x1-m+ >= ? x1-m+ : ;
y1 = y1-m+ >= ? y1-m+ : ;
a[size].x1 = x1,a[size].x2 = x2,a[size].y1 = oriy1 , a[size].y2 = y2 , a[size].flag = ;
b[size].x1 = orix1 , b[size].x2 = x2 , b[size].y1 = y1,b[size].y2 = y2 , b[size++].flag = ;
a[size].x1 = x1,a[size].x2 = x2,a[size].y1 = oriy1 , a[size].y2 = y2 , a[size].flag = ;
b[size].x1 = orix1 , b[size].x2 = x2 , b[size].y1 = y1,b[size].y2 = y2 , b[size++].flag = ;
}
ll ans = ;
a[size].x1 = w-m + >= ? w-m+ : , a[size].x2 = w , a[size].y1 = , a[size].y2 = h,a[size++].flag = ; //添加限制线
a[size].x1 = w-m + >= ? w-m+ : , a[size].x2 = w , a[size].y1 = , a[size].y2 = h,a[size++].flag = ;
ans += slove1();
size -= ;
b[size].x1 = ,b[size].x2 = w ,b[size].y1 = h-m+ >= ? h-m+ : ,b[size].y2 = h , b[size++].flag = ;
b[size].x1 = ,b[size].x2 = w ,b[size].y1 = h-m+ >= ? h-m+ : ,b[size].y2 = h , b[size++].flag = ;
ans += slove2();
if (m == )
printf("%lld\n",ans/);
else
printf("%lld\n",ans);
return ;
}
UESTC_秋实大哥与家 2015 UESTC Training for Data Structures<Problem E>的更多相关文章
- UESTC_秋实大哥搞算数 2015 UESTC Training for Data Structures<Problem N>
N - 秋实大哥搞算数 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Subm ...
- UESTC_秋实大哥打游戏 2015 UESTC Training for Data Structures<Problem H>
H - 秋实大哥打游戏 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Subm ...
- UESTC_秋实大哥去打工 2015 UESTC Training for Data Structures<Problem G>
G - 秋实大哥去打工 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Subm ...
- UESTC_秋实大哥与战争 2015 UESTC Training for Data Structures<Problem D>
D - 秋实大哥与战争 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Subm ...
- UESTC_秋实大哥与快餐店 2015 UESTC Training for Data Structures<Problem C>
C - 秋实大哥与快餐店 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Sub ...
- UESTC_秋实大哥与花 2015 UESTC Training for Data Structures<Problem B>
B - 秋实大哥与花 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Submi ...
- UESTC_秋实大哥与小朋友 2015 UESTC Training for Data Structures<Problem A>
A - 秋实大哥与小朋友 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Sub ...
- UESTC_秋实大哥掰手指 2015 UESTC Training for Dynamic Programming<Problem B>
B - 秋实大哥掰手指 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 2048/1024KB (Java/Others) Submit ...
- UESTC_秋实大哥与线段树 2015 UESTC Training for Data Structures<Problem M>
M - 秋实大哥与线段树 Time Limit: 3000/1000MS (Java/Others) Memory Limit: 65535/65535KB (Java/Others) Sub ...
随机推荐
- 使用skin++进行MFC界面美化范例
1.下载skin++皮肤库和皮肤库,skin++皮肤库主要包括:SkinPPWTL.dll,SkinPPWTL.lib,SkinPPWTL.h这三个文件.把这三个文件 拷贝到工程目录下. 2.在工程中 ...
- UVALive 6190 Beautiful Spacing (2012 Tokyo regional)
Beautiful Spacing 题意是给一个文本排版,求在满足题目所给要求的条件下,最长连续空格最小是多少. trick: 贪心地模拟是错的,至少无法证明正确性. 正解应该是二分答案+验证. 比较 ...
- MBI 跨国网络传销 金字塔诈骗 解密
马来西亚 反传销博客地址http://combatingillegalpyramidscheme.blogspot.jp/search/label/Mface 需要FQ访问 闽渝警方协作抓获一名公 ...
- Lua Interface基础使用
Lua是一种可爱的脚本语言,由Roberto Ierusalimschy.Waldemar Celes 和 Luiz Henrique de Figueiredo所组成并于1993年开发. 其设计目的 ...
- pyqt listview基础学习01
from decimal import * from PyQt4.QtGui import * from PyQt4.Qt import * from PyQt4.QtCore import * im ...
- PHP设计模式笔记一:准备工作 -- Rango韩老师 http://www.imooc.com/learn/236
一.编程字体选择 1.选择等宽字体 包括Courier New ,Consolas,Source Code Pro(推荐) 2.环境搭建(建议easyPHP) 二.开发符合PSR规范的基础框架 PSR ...
- 使用批处理bat作为日期系统日期的前三天
在管理server它经常是依据一天来推断载日期系统日志文件,例如,上周五,周一的需要上传日志.上传日志的日期前一天,日志文件命名的日期.这需要获得的日期的前三天.或之前n当天日期. 批量绑定vbs可以 ...
- hibernate 用hql做中文排序
用Hibernate+MySQL的童鞋是不是非常苦恼为什么MySQL不支持中文排序呢?没办法.仅仅有等utf8_unicode_cn 出来了.假设用hibernate即想实现跨库,又想不改代码怎样实现 ...
- iOS面试题集
现在寒假时间在家里面无法敲代码了,但是自己总要找些事情来做,回头想想马上就要开始就业了,所以不免要参加面试,于是便开始了面试题集的浏览和探索,今天下午我看了一部分的面试题感觉还是挺实用的,所以以后还是 ...
- ibatisnet框架使用说明
ibatis配置文件主要包括三个 sqlmap.config,providers.config,database.config,注意所有文件生成操作都为嵌入的资源.其中database.config主 ...