题意:有n个点和m条有向边构成的网络。每条边有两个花费:

d:毁坏这条边的花费
b:重建一条双向边的花费

寻找这样两个点集,使得点集s到点集t满足 毁坏全部S到T的路径的费用和 > 毁坏全部T到S的路径的费用和 + 重建这些T到S的双向路径的费用和。

思路1:

watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center" align="middle" alt="">

然后这个无源汇带上下界网络流的可行流问题的求解方法见这里~~

建图就是上面说的那样啦~最后推断有没有可行流就是求一下我们所构造的这个新的网络的最大流~然后推断一下这个最大流是否满流~(即推断最大流是否和附加源点的流出总量相等~~)

code:

#include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
#include<vector>
#include<string>
#include<queue>
#include<map>
#include<set>
#include<cmath>
#include<cstdlib>
using namespace std; #define INF 0x3f3f3f3f
#define PI acos(-1.0)
#define mem(a, b) memset(a, b, sizeof(a)) typedef pair<int,int> pii;
typedef long long LL;
//------------------------------
const int maxn = 210; int n,m; struct Edge{
int to, cap, rev;//终点 容量 反向边
Edge(int to_ = 0, int cap_ = 0, int rev_ = 0){
to = to_;
cap = cap_;
rev = rev_;
}
};
vector<Edge> g[maxn];
int level[maxn];//顶点到源点的距离标号
int iter[maxn]; void add_Edge(int from, int to, int cap){
Edge tmp1(to, cap, g[to].size());
g[from].push_back(tmp1);
Edge tmp2(from, 0, g[from].size()-1);
g[to].push_back(tmp2);
}
void bfs(int s){
memset(level, -1, sizeof(level));
queue<int> q;
level[s] = 0;
q.push(s);
while(!q.empty()){
int v = q.front();
q.pop();
for(int i = 0; i < g[v].size(); i++){
Edge& e = g[v][i];
if(e.cap > 0 && level[e.to] < 0){
level[e.to] = level[v] + 1;
q.push(e.to);
}
}
}
}
int dfs(int v, int t, int f){
if(v == t) return f;
for(int& i = iter[v]; i < g[v].size(); i++){
Edge& e = g[v][i];
if(e.cap > 0 && level[v] < level[e.to]){
int d = dfs(e.to, t, min(e.cap, f));
if(d > 0){
e.cap -= d;
g[e.to][e.rev].cap += d;
return d;
}
} }
return 0;
}
int max_flow(int s, int t){
int flow = 0;
for(;;){
bfs(s);
if(level[t] < 0) return flow;
memset(iter, 0, sizeof(iter));
int f;
while((f = dfs(s, t, INF)) > 0){
flow += f;
}
}
}
//------------------上面是最大流模板部分 正确---------------------- int sum;
int mi[maxn];//这个是用来保存每一个点的 入度-出度 的值,就是论文里的M(i); void init(){
for(int i = 0; i < maxn; i++){//网络流里的清空。不要忘记
g[i].clear();
}
memset(mi, 0, sizeof(mi));
scanf("%d%d",&n,&m);
int u, v, d, b;
for(int i = 1; i <= m; i++){
scanf("%d%d%d%d",&u, &v, &d, &b);
mi[u]-=d; mi[v]+=d;
add_Edge(u, v, b);//加边加上的是每条边的下界值
}
sum = 0;//sum保存的是源点的全部流出流量
for(int i = 1; i <= n; i++){
if(mi[i] < 0) add_Edge(i, n+1, -mi[i]);
else if(mi[i] > 0) {
add_Edge(0, i, mi[i]);
sum += mi[i];
}
}
}
void solve(){
int ans = max_flow(0, n+1);
if(ans == sum) printf("happy\n");
else printf("unhappy\n");
}
int main(){
int t;
int cas = 0;
scanf("%d",&t);
while(t--){
init();
printf("Case #%d: ",++cas);
solve();
}
return 0;
}

思路2:

阔以试想~假设对于全部单一的一个点组成的集合S来说,都不能满足

S到T的路径的费用和 > 毁坏全部T到S的路径的费用和 + 重建这些T到S的双向路径的费用和 的话,那么随意的点的集合构成的S集合也一定并不能满足上述条件~~~反之假设存在集合满足上述条件的话,就一定存在单一的点满足上述条件~~~~

这样我们事实上仅仅用枚举点然后推断就好啦。。。。。

Orz。。。

code:

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<iostream>
#include<vector>
using namespace std;
const int maxn = 205; int n, m; int D[maxn][maxn], B[maxn][maxn];
vector<int> in[maxn], out[maxn]; void init(){
for(int i = 0; i < maxn; i++){
in[i].clear();
out[i].clear();
}
memset(D,0,sizeof(D));
memset(B,0,sizeof(B));
scanf("%d%d",&n,&m);
int u, v, dd, bb;
for(int i = 1; i <= m; i++){
scanf("%d%d%d%d",&u,&v,&dd,&bb);
out[u].push_back(v);
in[v].push_back(u);
D[u][v] = dd;
B[u][v] = bb;
}
}
bool deal(int u){
int x = 0;
for(int i = 0; i < in[u].size(); i++){
int v = in[u][i];
x += D[v][u];
}
int y = 0;
for(int i = 0; i < out[u].size(); i++){
int v = out[u][i];
y = y + D[u][v] + B[u][v];
}
if(y < x) return true;
return false;
}
void solve(){
for(int i = 1; i <= n; i++){
if(deal(i)){
printf("unhappy\n");
return;
}
}
printf("happy\n");
}
int main(){
int t;
int cas = 0;
scanf("%d",&t);
while(t--){
init();
printf("Case #%d: ",++cas);
solve();
}
return 0;
}

hdu 4940 Destroy Transportation system( 无源汇上下界网络流的可行流推断 )的更多相关文章

  1. HDU 4940 Destroy Transportation system(无源汇上下界网络流)

    Problem Description Tom is a commander, his task is destroying his enemy’s transportation system. Le ...

  2. [Ahoi2014]支线剧情[无源汇有下界最小费用可行流]

    3876: [Ahoi2014]支线剧情 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 1538  Solved: 940[Submit][Statu ...

  3. hdu 4940 Destroy Transportation system (无源汇上下界可行流)

    Destroy Transportation system Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 131072/131072 ...

  4. hdu 4940 Destroy Transportation system(水过)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4940 Destroy Transportation system Time Limit: 2000/1 ...

  5. HDU 4940 Destroy Transportation system(无源汇有上下界最大流)

    看不懂题解以及别人说的集合最多只有一个点..... 然后试了下题解的方法http://blog.sina.com.cn/s/blog_6bddecdc0102uzka.html 首先是无源汇有上下界最 ...

  6. HDU 4940 Destroy Transportation system(2014 Multi-University Training Contest 7)

    思路:无源汇有上下界可行流判定, 原来每条边转化成  下界为D  上界为 D+B   ,判断是否存在可行流即可. 为什么呢?  如果存在可行流  那么说明对于任意的 S 集合流出的肯定等于 流入的, ...

  7. ZOJ 2314 Reactor Cooling(无源汇上下界网络流)

    http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=2314 题意: 给出每条边流量的上下界,问是否存在可行流,如果存在则输出. ...

  8. sgu 176 上下界网络流最小可行流带输出方案

    算法步骤: 1. 先将原图像最大可行流那样变换,唯一不同的是不加dst->src那条边来将它变成无源无汇的网络流图.直接跑一边超级源到超级汇的最大流. 2. 加上刚才没有加上的那条边p 3. 再 ...

  9. POJ 2396 Budget (上下界网络流有源可行流)

    转载: http://blog.csdn.net/axuan_k/article/details/47297395 题目描述: 现在要针对多赛区竞赛制定一个预算,该预算是一个行代表不同种类支出.列代表 ...

随机推荐

  1. Elasticsearch 1.4.X 的CORS设置

    最近将Elasticsearch由1.2.2升级到1.4.4后,sense工具无法使用了,它发到Elasticsearch集群的请求没有任何的响应.阅读了Elasticsearch的文档才了解到,这是 ...

  2. REF CURSOR和CURSOR

    REF CURSOR DECLARE TYPE TY_EMP_CUR IS REF CURSOR; V_Emp_Cur TY_EMP_CUR; V_Id EMP.ID%TYPE; BEGIN OPEN ...

  3. Python学习之路——类

    类: 类是将抽象的实物进行的划分. 在现实世界中如果我们将: 人类包含:男人.女人.孩子.老人等动物类包含:小猫.小狗.小兔子等 在代码世界中我也可以分类,例如将相同功能的代码放到一起,这就是分类. ...

  4. django virtualenv

    1. virtualenv virtualenv用于创建独立的Python环境,多个Python相互独立,互不影响,它能够:1. 在没有权限的情况下安装新套件2. 不同应用可以使用不同的套件版本3. ...

  5. asp.net 一般处理程序小优化

    使用asp.net mvc习惯了,最近项目中又开始使用asp.net,有大量的ajax方法调用,之前有两种方法来处理: Switch case :方法少还行,如果很多,就太蛋疼了,而且方法堆在一块,也 ...

  6. Android EditText 无法换行

    问题 关于控制是否换行的属性android:singleLine 当值为true的时候,只能一行,不换行 当值为false的时候,可以换行 但是现在遇到一个问题: <EditText andro ...

  7. Save Princess(丑数)

    Save Princess 时间限制:1000 ms  |  内存限制:65535 KB 难度:2   描述 Yesterday, the princess was kidnapped by a de ...

  8. Android 使用动态载入框架DL进行插件化开发

    如有转载,请声明出处: 时之沙: http://blog.csdn.net/t12x3456    (来自时之沙的csdn博客) 概述: 随着应用的不断迭代.应用的体积不断增大,项目越来越臃肿,冗余添 ...

  9. BZOJ 2718: [Violet 4]毕业旅行( 最长反链 )

    一不小心速度就成了#1.... 这道题显然是求最长反链, 最长反链=最小链覆盖.最小链覆盖就是先做一次floyd传递闭包, 再求最小路径覆盖. 最小路径覆盖=N - 二分图最大匹配. 所以把所有点拆成 ...

  10. js默认行为(也称默认事件)

    对应于智能社21课, 在浏览器的空白页面右击时会出现一个提示框,实际上这是用的document.oncontextmenu属性,如果用下面的代码就能够阻止这样的默认行为: <!DOCTYPE h ...