我是看不出这玩意儿和网络流有什么关系……
我们把图中的所有边都当成无向边加入图中,容量为\(inf\)
危桥的容量为\(2\)
从源点到\(a1,b1\)连边容量为\(an*2\),\(a2,b2\)到汇点连边容量\(bn*2\),相当于一次把两边都走完
然后跑一遍看看是否满流即可
然而这样会有一个问题,就是最终求得的最大流是\(a1\)流向\(b2\)或\(a2\)流向\(b1\)
于是再从源点向\(a1\)和\(b2\)连边,\(a2\)和\(b1\)向汇点连边,再跑一遍看看是否满流就是了
//minamoto
#include<bits/stdc++.h>
#define R register
#define inf 0x3f3f3f3f
#define fp(i,a,b) for(R int i=a,I=b+1;i<I;++i)
#define fd(i,a,b) for(R int i=a,I=b-1;i>I;--i)
#define go(u) for(R int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
#define gg(u) for(int &i=cur[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
inline int min(const R int &x,const R int &y){return x<y?x:y;}
using namespace std;
const int N=105,M=N*N*2;
struct eg{int v,nx,w;}e[M];int head[N],tot=1;
inline void add(R int u,R int v,R int w){
e[++tot]={v,head[u],w},head[u]=tot;
e[++tot]={u,head[v],w},head[v]=tot;
}
int dep[N],q[N],cur[N],S,T,h,t,u;
bool bfs(){
fp(i,S,T)cur[i]=head[i],dep[i]=-1;
q[h=t=1]=S,dep[S]=0;
while(h<=t){
int u=q[h++];
go(u)if(e[i].w&&dep[v]<0){
dep[v]=dep[u]+1,q[++t]=v;
if(v==T)return true;
}
}return false;
}
int dfs(int u,int lim){
if(u==T||!lim)return lim;
int flow=0,f;
gg(u)if(dep[v]==dep[u]+1&&(f=dfs(v,min(lim,e[i].w)))){
flow+=f,lim-=f;
e[i].w-=f,e[i^1].w+=f;
if(!lim)break;
}return flow;
}
int dinic(){int flow=0;while(bfs())flow+=dfs(S,inf);return flow;}
int n,m,a1,a2,an,b1,b2,bn;char s[N];int mmp[N][N];
inline void clr(){tot=1;memset(head,0,sizeof(head));}
void solve(){
clr();fp(i,1,n){
scanf("%s",s+1);
fp(j,1,n)mmp[i][j]=s[j]!='X'?s[j]!='N'?2:1:0;
}
fp(i,1,n)fp(j,i+1,n)if(mmp[i][j])add(i,j,mmp[i][j]==2?2:inf);
S=0,T=n+1,++a1,++b1,++a2,++b2;
add(S,a1,an<<1),add(S,b1,bn<<1),add(a2,T,an<<1),add(b2,T,bn<<1);
// printf("%d\n",dinic());
if(dinic()!=2*an+2*bn)return (void)(puts("No"));
clr();fp(i,1,n)fp(j,i+1,n)if(mmp[i][j])add(i,j,mmp[i][j]==2?2:inf);
add(S,a1,an<<1),add(S,b2,bn<<1),add(a2,T,an<<1),add(b1,T,bn<<1);
// printf("%d\n",dinic());
if(dinic()!=(2*an+2*bn))return (void)(puts("No"));
puts("Yes");
}
int main(){
// freopen("testdata.in","r",stdin);
while(~scanf("%d%d%d%d%d%d%d",&n,&a1,&a2,&an,&b1,&b2,&bn))solve();
return 0;
}
原文地址:https://www.cnblogs.com/bztMinamoto/p/10078058.html
时间: 2024-11-05 06:02:42