zoj 2314 Reactor Cooling
2014-11-10 16:33
344 查看
题意:网络中,每一条边拥有流量上限和下限,问是否存在可行流。
思路:最大流(经典模型,建图)。这个模型的建图方法略为神奇,原图中,边的容量改为流量上限-流量下限,建立源和汇,对每个顶点,计算恰好满足流量下限时是输入多还是输出多,设d[x]是点x输入和输出差的绝对值,如果该点输出多,连接该点到汇的边,容量是d[x],反之连接源到该点。最后检查源(汇)有关的边是否都满载,若满载则存在可行流。
我们可以这样理解,假设初始网络中满足每条边流量恰好为流量下限,但是这种情况下,网络不一定是平衡的,也就是有的点中“物质”会越来越多,有的点中“物质”会越来越少,我们就需要源/汇去供给/消耗不平衡的“物质”。
思路:最大流(经典模型,建图)。这个模型的建图方法略为神奇,原图中,边的容量改为流量上限-流量下限,建立源和汇,对每个顶点,计算恰好满足流量下限时是输入多还是输出多,设d[x]是点x输入和输出差的绝对值,如果该点输出多,连接该点到汇的边,容量是d[x],反之连接源到该点。最后检查源(汇)有关的边是否都满载,若满载则存在可行流。
我们可以这样理解,假设初始网络中满足每条边流量恰好为流量下限,但是这种情况下,网络不一定是平衡的,也就是有的点中“物质”会越来越多,有的点中“物质”会越来越少,我们就需要源/汇去供给/消耗不平衡的“物质”。
#include<iostream> #include<cmath> #include<cstring> #include<queue> #include<vector> #include<algorithm> #include<string.h> #include<cstdio> using namespace std; #define INF 100000010 #define maxn 210 struct Edge{ int u; int v; int cap; int flow; Edge(int u,int v,int c):u(u),v(v),cap(c),flow(0){} Edge(){}; }; Edge edges[maxn*maxn]; int ne; int head[maxn]; int next[maxn*maxn]; int n,m; int L[maxn*maxn]; int D[maxn]; void init(){ memset(head,-1,sizeof(head)); memset(D,0,sizeof(D)); ne=0; } int lv[maxn]; bool bfs(int s,int t){ memset(lv,-1,sizeof(lv)); lv[s]=0; queue<int> que; que.push(s); while(!que.empty()){ int cur=que.front(); que.pop(); for(int i=head[cur];i!=-1;i=next[i]){ Edge& e=edges[i]; if(lv[e.v]!=-1)continue; if(e.flow<e.cap){ lv[e.v]=lv[cur]+1; que.push(e.v); } } if(lv[t]!=-1)return 1; } return 0; } int cur[maxn]; int dfs(int x,int a){ if(x==n+1||a==0)return a; int re=0; for(int& i=cur[x];i!=-1;i=next[i]){ Edge& e=edges[i]; int t; if(lv[e.v]==(lv[x]+1)&& (t=dfs( e.v , min(a,e.cap-e.flow))) ){ edges[i].flow+=t; edges[i^1].flow-=t; re+=t; a-=t; if(a==0)break; } } return re; } int maxflow(int s,int t){ int flow=0; while(bfs(s,t)){ memcpy(cur,head,sizeof(head)); flow+=dfs(s,INF); } return flow; } void addedge(int u,int v,int c){ edges[ne]=Edge(u,v,c); next[ne]=head[u]; head[u]=ne; ne++; edges[ne]=Edge(v,u,0); next[ne]=head[v]; head[v]=ne; ne++; } int main(){ int t; cin>>t; while(t--){ cin>>n>>m; init(); for(int i=1;i<=m;i++){ int u,v,l,c; scanf("%d%d%d%d",&u,&v,&l,&c); addedge(u,v,c-l); D[u]+=l; D[v]-=l; L[i]=l; } for(int i=1;i<=n;i++){ if(D[i]>0) addedge(i,n+1,D[i]); else addedge(0,i,-D[i]); } maxflow(0,n+1); bool ok=1; for(int i=0;i<ne;i++){ if(edges[i].u==0){ if(edges[i].flow!=edges[i].cap)ok=0; } } if(ok){ cout<<"YES"<<endl; for(int i=1;i<=m;i++){ printf("%d\n",edges[(i-1)*2].flow+L[i]); } }else{ cout<<"NO"<<endl; } } return 0; }
相关文章推荐
- zoj 2314 Reactor Cooling
- ZOJ 2314 Reactor Cooling[无源汇上下界可行流]
- zoj 2314 Reactor Cooling--无源汇有上下界最大流--递归sap
- ZOJ 2314 Reactor Cooling(无源汇上下界网络流)
- 无源无汇上下界网络流(循环流) ZOJ 2314 Reactor Cooling
- zoj 2314 reactor cooling(无源汇有上下界可行流)
- zoj 2314 Reactor Cooling (无源汇有上下界的可行流)
- [ZOJ 2314]Reactor Cooling(有上下界的网络流)
- ZOJ - 2314 Reactor Cooling 无源汇上下界可行流
- zoj 2314 Reactor Cooling(无源汇上下界可行流)
- ZOJ 2314 Reactor Cooling
- [zoj] 2314 Reactor Cooling || 无源汇上下界可行流
- zoj 2314 Reactor Cooling (有上下界的网络流)
- ZOJ 2314 Reactor Cooling
- 【有上下界网络流】【ZOJ】2314 Reactor Cooling
- ZOJ_2314_Reactor Cooling_有上下界可行流模板
- zoj 2314 Reactor Cooling
- ZOJ 2314 Reactor Cooling 上下界网络流(无源汇可行流)
- 【无源汇有上下界可行流】ZOJ-2314 Reactor Cooling
- ZOJ 2314 Reactor Cooling 无源汇上下界可行流