Hdu 5301 Buildings 2015 Multi-University Training Contest 2

来源:互联网 发布:红色网络教育家园 编辑:程序博客网 时间:2024/05/17 20:21

Buildings

Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others)
Total Submission(s): 387    Accepted Submission(s): 81


Problem Description
Your current task is to make a ground plan for a residential building located in HZXJHS. So you must determine a way to split the floor building with walls to make apartments in the shape of a rectangle. Each built wall must be paralled to the building's sides.

The floor is represented in the ground plan as a large rectangle with dimensions n×m, where each apartment is a smaller rectangle with dimensions a×b located inside. For each apartment, its dimensions can be different from each other. The number a and b must be integers.

Additionally, the apartments must completely cover the floor without one 1×1 square located on (x,y). The apartments must not intersect, but they can touch.

For this example, this is a sample of n=2,m=3,x=2,y=2.



To prevent darkness indoors, the apartments must have windows. Therefore, each apartment must share its at least one side with the edge of the rectangle representing the floor so it is possible to place a window.

Your boss XXY wants to minimize the maximum areas of all apartments, now it's your turn to tell him the answer.
 

Input
There are at most 10000 testcases.
For each testcase, only four space-separated integers, n,m,x,y(1n,m108,n×m>1,1xn,1ym).
 

Output
For each testcase, print only one interger, representing the answer.
 

Sample Input
2 3 2 23 3 1 1
 

Sample Output
12
Hint
Case 1 :
You can split the floor into five 1×1 apartments. The answer is 1.Case 2:
You can split the floor into three 2×1 apartments and two 1×1 apartments. The answer is 2.
If you want to split the floor into eight 1×1 apartments, it will be unacceptable because the apartment located on (2,2) can't have windows.
 

Source
2015 Multi-University Training Contest 2
 


比赛的时候真的是Wa到底了,简单粗暴的都写了。

题解:假设没有坏点 ans = (min(n,m)+1 )/2,现在有了坏点,想象下坏点带来的变化,不要想的太复杂了。

队友还有另外一个办法A掉了,灌水的思想,二分答案。

#include<iostream>#include<algorithm>#include<cstdio>using namespace std;int main(){    int n,m,x,y;    while(~scanf("%d%d%d%d",&n,&m,&x,&y)){        if(n>m){swap(n,m),swap(x,y); }        if(n==1&m==1){puts("0");continue; }        if(n==1||m==1){puts("1");continue; }        int ans=(n+1)/2;        if(x==y && n==m && (n%2==1) && (x==(n+1)/2))            ans--;        else {            x=min(x,n-x+1);            y=min(y,m-y+1);            ans=max(ans,min(n-x,y));            ans=min(ans,(m+1)/2);        }        printf("%d\n",ans);    }    return 0;}

#include<cstdio>#include<cmath>#include<algorithm>#include<iostream>using namespace std;#define sf scanf#define mx 1000000009long long n,m,x,y;bool check(long long x,long long y){        return x>0&&x<=n&&y>0&&y<=m;}bool full(long long t){        if((x==(n+1)/2)&&(y==(m+1)/2)) return true;        else if(t*2>=m) return true;        else return false;}int main(){        while(~sf("%lld%lld%lld%lld",&n,&m,&x,&y))        {                long long ans=m;                if(n<m){swap(n,m);swap(x,y);}                long long l =  m/2,r=m;                //cout<<l<<" "<<r<<endl;                while(l<=r)                {                        long long mid = (l+r)/2;                        //cout<<l<<" "<<r<<" "<<mid<<endl;                        bool flag = true;                        if(check(x-1,y)) if(mid<x-1&&mid<y&&mid<m-y+1) flag=false;                        if(check(x+1,y)) if(mid<n-x&&mid<y&&mid<m-y+1) flag=false;                        if(check(x,y-1)) if(mid<x&&mid<n-x+1&&mid<y-1) flag=false;                         if(check(x,y+1)) if(mid<x&&mid<n-x+1&&mid<m-y) flag=false;                        if(flag&&full(mid)){ans = mid;r=mid-1;}else l=mid+1;                }                printf("%d\n",ans);        }}


0 0
原创粉丝点击