题目链接:https://vjudge.net/contest/144904#problem/A

题意:给定一个有向网络,每条边均有一个容量。问是否存在一个从点1到点N,流量为C的流。如果不存在,是否可以恰好修改一条弧的容量,使得存在这样的流?

分析:

首先找到最大流,如果发现大于等于C,就得到解,如果小于C的话,枚举最小割。这时,之前的最大流保存下来,清空流量,改变最小割的容量,再求最大流。

include <bits/stdc++.h>
using namespace std; const int maxn = + ;
const int INF = 0x3f3f3f3f; struct Edge {
int from,to,cap,flow;
}; bool operator < (const Edge& a,const Edge& b) {
return a.from < b.from || (a.from==b.from&&a.to<b.to);
} struct Dinic {
int n,m,s,t;
vector<Edge> edges;
vector<int> G[maxn];
bool vis[maxn];
int d[maxn];
int cur[maxn]; void init(int n) {
for(int i=;i<n;i++)
G[i].clear();
edges.clear();
} void ClearFlow() {
for(int i=;i<edges.size();i++) {
edges[i].flow = ;
}
} void AddEdge(int from,int to,int cap) {
edges.push_back((Edge){from,to,cap,});
edges.push_back((Edge){to,from,,});
m = edges.size();
G[from].push_back(m-);
G[to].push_back(m-);
} bool BFS() {
memset(vis,,sizeof(vis));
queue<int> Q;
Q.push(s);
vis[s] = ;
d[s] = ;
while(!Q.empty()) {
int x = Q.front();
Q.pop();
for(int i=;i<G[x].size();i++) {
Edge& e = edges[G[x][i]];
if(!vis[e.to]&&e.cap>e.flow) {
vis[e.to] = ;
d[e.to] = d[x] + ;
Q.push(e.to);
}
}
}
return vis[t];
} int DFS(int x,int a) {
if(x==t||a==) return a;
int flow =,f;
for(int& i=cur[x];i<G[x].size();i++) {
Edge& e = edges[G[x][i]];
if(d[x]+==d[e.to]&&(f=DFS(e.to,min(a,e.cap-e.flow)))>) {
e.flow +=f;
edges[G[x][i]^].flow -=f;
flow +=f;
a-=f;
if(a==) break;
}
}
return flow;
} int Maxflow(int s,int t) {
this->s = s;
this->t = t;
int flow = ;
while(BFS()) {
memset(cur,,sizeof(cur));
flow +=DFS(s,INF);
}
return flow;
} vector<int> Mincut() {
vector<int> ans;
for(int i=;i<edges.size();i++) {
Edge& e = edges[i];
if(vis[e.from]&&!vis[e.to]&&e.cap>)
ans.push_back(i);
}
return ans;
} void Reduce () {
for(int i=;i<edges.size();i++)
edges[i].cap -=edges[i].flow;
} }; Dinic g; int main()
{
int kase = ;
int n,e,c;
while(scanf("%d%d%d",&n,&e,&c)==&&n) {
g.init(n);
for(int i=;i<e;i++) {
int u,v,cap;
scanf("%d%d%d",&u,&v,&cap);
u--;v--;
g.AddEdge(u,v,cap);
}
printf("Case %d: ",kase ++);
int flow = g.Maxflow(,n-);
if(flow>=c) printf("possible\n"); else {
vector<int> cut = g.Mincut();
g.Reduce();
vector<Edge> ans;
for(int i=;i<cut.size();i++) {
Edge& e = g.edges[cut[i]];
int temp = e.cap; ///
e.cap = c;
g.ClearFlow();
if(flow+g.Maxflow(,n-)>=c)
ans.push_back(e);
e.cap = temp; ///
}
if(ans.empty())
printf("not possible\n");
else {
sort(ans.begin(),ans.end());
printf("possible option:(%d,%d)",ans[].from+,ans[].to + );
for(int i=;i<ans.size();i++) {
printf(",(%d,%d)",ans[i].from+,ans[i].to+);
}
puts("");
}
}
} return ;
}

最新文章

  1. maven 加入json-lib.jar 报错 Missing artifact net.sf.json-lib:json-lib:jar:2.4:compile
  2. 大熊君大话NodeJS之------Connect中间件模块(第一季)
  3. redis配置
  4. JVM中的垃圾收集算法和Heap分区简记
  5. phonegap+html5开发app的一些总结
  6. 给input元素添加float. 去除IE6 下input的空隙
  7. 丑数&lt;数学技巧&gt;
  8. 【Arduino】2017年电子设计大赛B题 滚球控制系统|板球系统
  9. http get(swift and oc)
  10. sql基础题目测试及正确答案
  11. Ubuntu16.0.4下搭建pycharm 2018.3.22
  12. Redis5种常用的数据结构
  13. 使用matplotlib画饼图
  14. mtr
  15. 我做SAP CRM One Order redesign的一些心得体会
  16. 【Docker】第二篇 Docker镜像管理
  17. 【转】2012年7月9 – 知名网页游戏公司 PHP高级工程师 最新面试题
  18. PHP Global定义全局变量使用说明
  19. JavaScript年月日和时间戳互转
  20. 通过非聚集索引让select count(*) from 的查询速度提高几十倍、甚至千倍

热门文章

  1. 【转载】查看freebsd 服务器硬件信息
  2. 在Ubuntu上安装网易云音乐
  3. Oracle知识分类之常见规范
  4. 另一种在WINFORM中使用XNA的方法
  5. IIC总线
  6. jquery懒加载jquery.lazyload.js
  7. Python学习笔记(一)python基础与函数
  8. java 读写文件
  9. python中常用的模块的总结
  10. NOI 09:奇数求和