[DLX重复覆盖] hdu 3498 whosyourdaddy

来源:互联网 发布:什么是数据库中的事物 编辑:程序博客网 时间:2024/05/21 22:59

题意:

给N个怪,M个关系。

每个关系代表a和b是邻居。

然后问每次攻击你可以攻击一个怪以及它的全部邻居

问最少需要几次攻击能把怪全部杀死。

思路:

怪为行和列,然后对面每个怪的邻居都是这个怪的列建图。

也是比较裸的重复覆盖。

代码:

#include"cstdlib"#include"cstdio"#include"cstring"#include"cmath"#include"queue"#include"algorithm"#include"iostream"#include"map"#include"vector"#define mod 1000000007#define ll long longusing namespace std;#define N 1010*100#define RN 1010#define CN 1010struct DLX{    int n,m,C;    int U[N],D[N],L[N],R[N],Row[N],Col[N];    int H[RN],S[CN],cnt,ans[RN];    void init(int _n,int _m)    {        n=_n;        m=_m;        for(int i=0; i<=m; i++)        {            S[i]=0;            U[i]=D[i]=i;            L[i]=(i==0?m:i-1);            R[i]=(i==m?0:i+1);        }        C=m;        for(int i=1; i<=n; i++) H[i]=-1;    }    void link(int x,int y)    {        C++;        Row[C]=x;        Col[C]=y;        S[y]++;        U[C]=U[y];        D[C]=y;        D[U[y]]=C;        U[y]=C;        if(H[x]==-1) H[x]=L[C]=R[C]=C;        else        {            L[C]=L[H[x]];            R[C]=H[x];            R[L[H[x]]]=C;            L[H[x]]=C;        }    }    void del(int x)    {        for(int i=D[x]; i!=x; i=D[i])        {            R[L[i]]=R[i];            L[R[i]]=L[i];        }    }    void rec(int x)    {        for(int i=U[x]; i!=x; i=U[i])        {            R[L[i]]=i;            L[R[i]]=i;        }    }    int used[CN];    int h()    {        int sum=0;        for(int i=R[0]; i!=0; i=R[i]) used[i]=0;        for(int i=R[0]; i!=0; i=R[i])        {            if(used[i]==0)            {                sum++;                used[i]=1;                for(int j=D[i]; j!=i; j=D[j]) for(int k=R[j]; k!=j; k=R[k]) used[Col[k]]=1;            }        }        return sum;    }    void dance(int x)    {        if(x+h()>=cnt) return ;        if(R[0]==0)        {            cnt=min(cnt,x);            return ;        }        int now=R[0];        for(int i=R[0]; i!=0; i=R[i])        {            if(S[i]<S[now])                now=i;        }        for(int i=D[now]; i!=now; i=D[i])        {            del(i);            for(int j=R[i]; j!=i; j=R[j]) del(j);            dance(x+1);            for(int j=L[i]; j!=i; j=L[j]) rec(j);            rec(i);        }        return ;    }} dlx;int main(){    int n,m;    while(scanf("%d%d",&n,&m)!=-1)    {        int mp[88][88];        memset(mp,0,sizeof(mp));        while(m--)        {            int a,b;            scanf("%d%d",&a,&b);            mp[a][b]=1;            mp[b][a]=1;        }        dlx.init(n,n);        for(int i=1;i<=n;i++)        {            dlx.link(i,i);            for(int j=1;j<=n;j++)            {                if(mp[i][j]==1) dlx.link(i,j);            }        }        dlx.cnt=999;        dlx.dance(0);        printf("%d\n",dlx.cnt);    }    return 0;}


0 0
原创粉丝点击