随机数据跑的飞起但是BZOJ的数据卡的我几乎过不了。。。。
匈牙利果然迷之复杂度。
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #include<vector> #define maxv 6050 #define maxe 10000050 using namespace std; int a,b,m,nume=1,g[maxv],x[maxv],y[maxv],uu,vv,flag[maxv],times=0,pos[maxv],rec=1,ans=0,kr=0; int ly[maxv],used[maxv],vis[maxv]; struct edge { int v,nxt; }e[maxe]; struct data { int val,id; data (int val,int id):val(val),id(id) {} data () {} }d[maxv]; vector <int> v[maxv]; bool cmp(data x,data y) {return (x.val&1)<(y.val&1);} void addedge(int u,int v) { e[++nume].v=v; e[nume].nxt=g[u]; g[u]=nume; } bool check(int x,int y) { if (!((x^y)&1)) return true; int ans=0,ret=x|y; while (ret) {if (ret&1) ans++;ret>>=1;} return ans&1; } void build_base() { for (int i=1;i<=b;i++) for (int j=i+1;j<=b;j++) if (!check(y[i],y[j])) { if (y[i]&1) addedge(j,i); else addedge(i,j); } } void ban(int x) { for (unsigned int i=0;i<v[x].size();i++) { int to=v[x][i]; vis[to]++; } } bool hungary(int x) { if (vis[x]==times) return false; for (int i=g[x];i;i=e[i].nxt) { int v=e[i].v; if ((used[v]==kr) || (vis[v]==times)) continue; used[v]=kr; if ((ly[v]==-1) || (hungary(ly[v]))) { ly[v]=x; return true; } } return false; } int main() { scanf("%d%d%d",&a,&b,&m); rec=a+1; for (int i=1;i<=a;i++) { scanf("%d",&x[i]); d[i]=data(x[i],i); } for (int i=1;i<=b;i++) scanf("%d",&y[i]); for (int i=1;i<=m;i++) { scanf("%d%d",&uu,&vv); v[uu].push_back(vv); } build_base();sort(d+1,d+a+1,cmp); for (int i=1;i<=a;i++) if (d[i].val&1) {rec=i;break;} for (int i=0;i<=rec-1;i++) for (int j=rec-1;j<=a;j++) { times++;int ss=0; for (int k=1;k<=b;k++) vis[k]=0; if (i>=1) {ban(d[i].id);ss++;} if (j>=rec) {ban(d[j].id);ss++;} for (int k=1;k<=b;k++) if (vis[k]!=ss) vis[k]=times;else vis[k]=0; int ret=0,cnt=0; for (int k=1;k<=b;k++) { ly[k]=-1;used[k]=0; if (vis[k]==times) cnt++; } kr=0; for (int k=1;k<=b;k++) { kr++; if (vis[k]==times) continue; if (y[k]&1) continue; if (hungary(k)) ret++; } ans=max(ans,b-cnt-ret+ss); } printf("%d\n",ans); return 0; }