POJ - 3179 Corral the Cows【离散化】【前缀和】

【题目描述】
Farmer John wishes to build a corral for his cows. Being finicky beasts, they demand that the corral be square and that the corral contain at least C (1 <= C <= 500) clover fields for afternoon treats. The corral’s edges must be parallel to the X,Y axes.

FJ’s land contains a total of N (C <= N <= 500) clover fields, each a block of size 1 x 1 and located at with its lower left corner at integer X and Y coordinates each in the range 1…10,000. Sometimes more than one clover field grows at the same location; such a field would have its location appear twice (or more) in the input. A corral surrounds a clover field if the field is entirely located inside the corral’s borders.

Help FJ by telling him the side length of the smallest square containing C clover fields.

【输入】
Line 1: Two space-separated integers: C and N

Lines 2…N+1: Each line contains two space-separated integers that are the X,Y coordinates of a clover field.

【输出】
Line 1: A single line with a single integer that is length of one edge of the minimum size square that contains at least C clover fields.

【样例输入】
3 4
1 2
2 1
4 1
5 2

【样例输出】
4

题目链接:https://vjudge.net/problem/POJ-3179

lyd老师tql

代码如下:

#include 
#include 
#include 
#include 
using namespace std;
static const int MAXN=500;
int mp[MAXN+10][MAXN+10];
struct Node{
    int x,y;
    bool operator < (const Node &r) const {
        if(x==r.x)
            return y<r.y;
        return x<r.x;
    }
};
vector<Node> point;
vector<int> x;
vector<int> y;
int main()
{
    std::ios::sync_with_stdio(false);
    std::cin.tie(0),cout.tie(0);
    int C,N;
    cin>>C>>N;
    int a,b;
    for(int i=1;i<=N;i++)
    {
        cin>>a>>b;
        point.push_back({a,b});
        x.push_back(a);
        y.push_back(b);
    }
    sort(point.begin(),point.end());
    sort(x.begin(),x.end());
    sort(y.begin(),y.end());
    x.erase(unique(x.begin(),x.end()),x.end());
    y.erase(unique(y.begin(),y.end()),y.end());
    int n=x.size();
    int m=y.size();
    int cnt=0;
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
        {
            while(cnt<N && point[cnt].x==x[i-1] && point[cnt].y==y[j-1])
            {
                mp[i][j]++;
                cnt++;
            }
            mp[i][j]+=mp[i-1][j]+mp[i][j-1]-mp[i-1][j-1];
        }
    x.push_back(INT_MAX);
    y.push_back(INT_MAX);
    int ans=INT_MAX;
    for(int x1=0;x1<n;x1++)
    {
        int x2=x1+1;
        int y1=0;
        int y2=y1+1;
        int len=0;
        int temp=mp[x2][y2]-mp[x1][y2]-mp[x2][y1]+mp[x1][y1];
        while(1)
        {
            while(temp<C && (x2<n || y2<m))
            {
                len=min(x[x2]-x[x1],y[y2]-y[y1]);
                while(x[x2]-x[x1]<=len) x2++;
                while(y[y2]-y[y1]<=len) y2++;
                temp=mp[x2][y2]-mp[x1][y2]-mp[x2][y1]+mp[x1][y1];
            }
            if(temp<C) break;
            ans=min(ans,len+1);
            y1++;
            if(y1==m) break;
            if(y1>=y2)
            {
                y2=y1+1;
                len=0;
            }
            else len-=y[y1]-y[y1-1];
            while(x[x2-1]-x[x1]>len) x2--;
            temp=mp[x2][y2]-mp[x1][y2]-mp[x2][y1]+mp[x1][y1];
        }
    }
    cout<<ans<<endl;
    return 0;
}

你可能感兴趣的:(前缀和,离散化)