传送门:BZOJ1052
傻逼题。
二分一个长度,注意到每次正方形必然落在某个角上,枚举判断即可。
好久不见的1A……
代码上的小细节见下。
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <iostream>
using namespace std;
const int INF=0x3f3f3f3f;
struct Point{
int x,y;
Point(){
x=y=0;
}
};
struct Matrix{
Point basic[20005];
int size;
Matrix(){
size=0;
}
};
int n;
Matrix T;
void GetPoint(Point& BLC,Point& RC,Matrix a) //获得矩形a的左下角和右下角
{
int minx=INF,maxx=-INF;
int miny=INF,maxy=-INF;
for(int i=1;i<=a.size;i++){
minx=min(minx,a.basic[i].x);
maxx=max(maxx,a.basic[i].x);
miny=min(miny,a.basic[i].y);
maxy=max(maxy,a.basic[i].y);
}
BLC.x=minx;BLC.y=miny;
RC.x=maxx;RC.y=maxy;
}
void Cut(Matrix& a,Point BLC,Point RC) //擦掉正方形覆盖区域
{
Matrix b;
for(int i=1;i<=a.size;i++)
if(!((BLC.x<=a.basic[i].x&&a.basic[i].x<=RC.x)&&(BLC.y<=a.basic[i].y&&a.basic[i].y<=RC.y))){
b.size++;
b.basic[b.size].x=a.basic[i].x;
b.basic[b.size].y=a.basic[i].y;
}
a=b;
}
bool Check(Matrix& a,int T) //判断矩阵能否被正方形完全覆盖
{
Point BLC,RC;
GetPoint(BLC,RC,a);
return ((RC.x-BLC.x+1<=T)&&(RC.y-BLC.y+1<=T));
}
void Update(Matrix& a,int kind,int T) //修改矩形
{
Point BLC,RC;
GetPoint(BLC,RC,a);
//if(kind==1) //左下角
//RC.x=BLC.x+T-1,RC.y=BLC.y+T-1;
if(kind==2) //左上角
BLC.y=RC.y+1-T;
if(kind==3) //右上角
BLC.x=RC.x+1-T,BLC.y=RC.y+1-T;
if(kind==4) //右下角
BLC.x=RC.x+1-T;
RC.x=BLC.x+T-1,RC.y=BLC.y+T-1;
Cut(a,BLC,RC);
}
bool Judge(Matrix a,int T) //暴力枚举,判断给定长度是否可行
{
for(int i=1;i<=4;i++)
for(int j=1;j<=4;j++){
Matrix b=a;
Update(b,i,T);
Update(b,j,T);
if(Check(b,T))
return true;
}
return false;
}
void Solve(Matrix a) //求解问题
{
int l=1,r=INF;
while(l<r){
int mid=(l+r)/2;
bool flag=Judge(a,mid);
if(flag)
r=mid;
else
l=mid+1;
}
printf("%d\n",l-1);
}
void Readdata()
{
freopen("loli.in","r",stdin);
scanf("%d",&n);
for(int i=1;i<=n;i++)
scanf("%d%d",&T.basic[i].x,&T.basic[i].y);
T.size=n;
}
void Close()
{
fclose(stdin);
fclose(stdout);
}
int main()
{
Readdata();
Solve(T);
Close();
return 0;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。
原文地址:http://blog.csdn.net/le_ballon_rouge/article/details/47982035