hdu2389(HK算法)

 

传送门:Rain on your Parade

题意:t个单位时间后开始下雨,给你N个访客的位置(一维坐标平面内)和他的移动速度,再给M个雨伞的位置,问在下雨前最多有多少人能够拿到雨伞(两个人不共用一把伞)。

分析:这题匈牙利算法撸不过,只好去学习Hopcroft-Carp算法,复杂度为O(sqrt(V)*E),该算法预先找好增广路径集,避免了许多没不要的匹配.

#include <cstdio>

#include <cstring>

#include <string>

#include <cmath>

#include <iostream>

#include <algorithm>

#include <queue>

#include <cstdlib>

#include <stack>

#include <vector>

#include <set>

#include <map>

#define LL long long

#define mod 100000000

#define inf 0x3f3f3f3f

#define eps 1e-6

#define N 10010

#define FILL(a,b) (memset(a,b,sizeof(a)))

#define lson l,m,rt<<1

#define rson m+1,r,rt<<1|1

#define PII pair<int,int>

using namespace std;

int dx[N],dy[N],matchx[N],matchy[N];

int vis[N],dis,n,m,t;

vector<int>g[N];

struct node

{

    int x,y,z;

}s[N];

bool search_path()

{

    queue<int>que;

    dis=inf;

    FILL(dx,-1);FILL(dy,-1);

    for(int i=1;i<=n;i++)

    {

        if(matchx[i]==-1)

        {

            que.push(i);

            dx[i]=0;

        }

    }

    while(!que.empty())

    {

        int u=que.front();

        que.pop();

        if(dx[u]>dis)break;

        for(int i=0,sz=g[u].size();i<sz;i++)

        {

            int v=g[u][i];

            if(dy[v]==-1)

            {

                dy[v]=dx[u]+1;

                if(matchy[v]==-1)dis=dy[v];

                else

                {

                    dx[matchy[v]]=dy[v]+1;

                    que.push(matchy[v]);

                }

            }

        }

    }

    return dis!=inf;

}

int dfs(int u)

{

    for(int i=0,sz=g[u].size();i<sz;i++)

    {

        int v=g[u][i];

        if(!vis[v]&&dy[v]==dx[u]+1)

        {

            vis[v]=1;

            if(matchy[v]!=-1&&dy[v]==dis)continue;

            if(matchy[v]==-1||dfs(matchy[v]))

            {

                matchy[v]=u;

                matchx[u]=v;

                return 1;

            }

        }

    }

    return 0;

}

int HK()

{

    int res=0;

    FILL(matchx,-1);FILL(matchy,-1);

    while(search_path())

    {

        FILL(vis,0);

        for(int i=1;i<=n;i++)

            if(matchx[i]==-1&&dfs(i))res++;

    }

    return res;

}

bool judge(int a,int b,int x,int y,int z)

{

    return (a-x)*(a-x)+(b-y)*(b-y)<=(z*t)*(z*t);

}

int main()

{

    int T,cas=1;

    scanf("%d",&T);

    while(T--)

    {

        scanf("%d%d",&t,&n);

        for(int i=1;i<=n;i++)g[i].clear();

        for(int i=1;i<=n;i++)

            scanf("%d%d%d",&s[i].x,&s[i].y,&s[i].z);

        scanf("%d",&m);

        for(int i=1;i<=m;i++)

        {

            int x,y;

            scanf("%d%d",&x,&y);

            for(int j=1;j<=n;j++)

            {

                if(judge(x,y,s[j].x,s[j].y,s[j].z))

                    g[j].push_back(i);

            }

        }

        int ans=HK();

        printf("Scenario #%d:\n%d\n",cas++,ans);

        puts("");

    }

}
View Code

 

你可能感兴趣的:(HDU)