1834: [ZJOI2010]network 网络扩容

Time Limit: 3 Sec  Memory Limit: 64 MB
Submit: 2701  Solved: 1368
[Submit][Status][Discuss]

Description

给定一张有向图,每条边都有一个容量C和一个扩容费用W。这里扩容费用是指将容量扩大1所需的费用。求: 1、 在不扩容的情况下,1到N的最大流; 2、 将1到N的最大流增加K所需的最小扩容费用。

Input

输入文件的第一行包含三个整数N,M,K,表示有向图的点数、边数以及所需要增加的流量。 接下来的M行每行包含四个整数u,v,C,W,表示一条从u到v,容量为C,扩容费用为W的边。

Output

输出文件一行包含两个整数,分别表示问题1和问题2的答案。

Sample Input

5 8 2
1 2 5 8
2 5 9 9
5 1 6 2
5 1 1 8
1 2 8 7
2 5 4 9
1 2 1 1
1 4 2 1

Sample Output

13 19
 
 
 
【题解】
网络流和费用流的结合。
第一问很简单,直接跑一遍dinic即可。
第二问是费用流,将原图上的每条边上建立一条附属边,流量为k,费用为扩容费用,然后跑费用流即可。
 #include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<algorithm>
#include<queue>
using namespace std;
#define INF 1000000000
#define MAXN 5010
struct node{int x,y,next,v,c,rel;}e[MAXN*],edge[MAXN*];
int n,m,k,len,ans,Link[MAXN],level[MAXN],vis[MAXN],dis[MAXN],lastnode[MAXN],lastedge[MAXN],q[MAXN*];
inline int read()
{
int x=,f=; char ch=getchar();
while(!isdigit(ch)) {if(ch=='-') f=-; ch=getchar();}
while(isdigit(ch)) {x=x*+ch-''; ch=getchar();}
return x*f;
}
void insert(int x,int y,int v,int c)
{
e[++len].next=Link[x];Link[x]=len;e[len].x=x;e[len].y=y;e[len].v=v;e[len].c=c;e[len].rel=len+;
e[++len].next=Link[y];Link[y]=len;e[len].x=y;e[len].y=x;e[len].v=;e[len].c=-c;e[len].rel=len-;
}
bool bfs()
{
memset(level,-,sizeof(level));
int head=,tail=; q[]=; level[]=;
while(++head<=tail)
for(int i=Link[q[head]];i;i=e[i].next)
if(level[e[i].y]<&&e[i].v)
{
q[++tail]=e[i].y;
level[q[tail]]=level[q[head]]+;
}
return level[n]>=;
}
int dinic(int x,int flow)
{
if(x==n) return flow;
int maxflow=,d=;
for(int i=Link[x];i&&maxflow<flow;i=e[i].next)
if(level[e[i].y]==level[x]+&&e[i].v)
if(d=dinic(e[i].y,min(e[i].v,flow-maxflow)))
{
maxflow+=d;
e[i].v-=d;
e[e[i].rel].v+=d;
}
if(!maxflow) level[x]=-;
return maxflow;
}
void solve1()
{
int d=;
ans=;
while(bfs())
while(d=dinic(,INF))
ans+=d;
printf("%d ",ans);
}
bool spfa()
{
memset(vis,,sizeof(vis));
memset(dis,,sizeof(dis));
int head=,tail=,oo=dis[];
q[]=; vis[]=; dis[]=;
while(++head<=tail)
{
int x=q[head];
for(int i=Link[x];i;i=e[i].next)
if(dis[x]+e[i].c<dis[e[i].y]&&e[i].v)
{
dis[e[i].y]=dis[x]+e[i].c;
if(!vis[e[i].y])
{
q[++tail]=e[i].y;
vis[e[i].y]=;
}
lastnode[e[i].y]=x; lastedge[e[i].y]=i;
}
vis[x]=;
}
return dis[n]<oo;
}
void cost()
{
int d=k;
for(int i=n;i!=;i=lastnode[i])
if(e[lastedge[i]].v<d)
d=e[lastedge[i]].v;
for(int i=n;i!=;i=lastnode[i])
{
int j=lastedge[i];
e[j].v-=d;
e[e[j].rel].v+=d;
ans+=d*e[j].c;
}
k-=d;
}
void solve2()
{
ans=;
while(k)//控制1点的流量,相当于一个超级源的作用
{
spfa();
cost();
}
printf("%d\n",ans);
}
int main()
{
freopen("cin.in","r",stdin);
freopen("cout.out","w",stdout);
n=read(); m=read(); k=read();
for(int i=;i<=m;i++)
{
int x=read(),y=read(),v=read(),c=read();
insert(x,y,v,);
edge[i].x=x; edge[i].y=y; edge[i].c=c;
}
solve1();
for(int i=;i<=m;i++) insert(edge[i].x,edge[i].y,k,edge[i].c);
solve2();
return ;
}

【bzoj1834】[ZJOI2010]network 网络扩容的更多相关文章

  1. BZOJ1834 [ZJOI2010]network 网络扩容 【最大流,费用流】

    1834: [ZJOI2010]network 网络扩容 Time Limit: 3 Sec  Memory Limit: 64 MB Submit: 3394  Solved: 1774 [Subm ...

  2. [BZOJ1834][ZJOI2010]network 网络扩容 最大流+费用流

    1834: [ZJOI2010]network 网络扩容 Time Limit: 3 Sec  Memory Limit: 64 MB Submit: 3330  Solved: 1739 [Subm ...

  3. bzoj1834: [ZJOI2010]network 网络扩容 费用流

    bzoj1834 给定一张有向图,每条边都有一个容量C和一个扩容费用W.这里扩容费用是指将容量扩大1所需的费用. 求: 1.在不扩容的情况下,1到N的最大流: 2.将1到N的最大流增加K所需的最小扩容 ...

  4. 【费用流】bzoj1834: [ZJOI2010]network 网络扩容

    还是稍微记一下这个拆点模型吧 Description 给定一张有向图,每条边都有一个容量C和一个扩容费用W.这里扩容费用是指将容量扩大1所需的费用. 求:  1.在不扩容的情况下,1到N的最大流:  ...

  5. 2018.10.13 bzoj1834: [ZJOI2010]network 网络扩容(最大流+费用流)

    传送门 网络流水题啊. 第一问直接放心跑最大流(本来还以为有什么tricktricktrick). 第二问就直接把原来的边(u,v,c,w)(u,v,c,w)(u,v,c,w)变成(u,v,c,0)( ...

  6. 【最大流】【费用流】bzoj1834 [ZJOI2010]network 网络扩容

    引用题解: 最大流+费用流. 第一问最大流即可. 第二问为“最小费用最大流”. 由题意,这一问的可转化为在上一问的“残量网络”上,扩大一些边的容量,使能从新的图中的最大流为k. 那么易得:对于还有剩余 ...

  7. BZOJ1834 [ZJOI2010]network 网络扩容(最小费用最大流)

    挺直白的构图..最小费用最大流的定义. #include<cstdio> #include<cstring> #include<queue> #include< ...

  8. bzoj1834 [ZJOI2010]network 网络扩容

    第一问跑最大流,第二问新建一条边连接0和1,流量为上第一问的答案+k,费用为0,接下来图中每条边拆成两条边,第一条容量为C费用为0,第二条容量无穷费用为W,再跑一遍费用流即可. 代码 #include ...

  9. 【BZOJ1834】[ZJOI2010]network 网络扩容 最大流+最小费用流

    [BZOJ1834][ZJOI2010]network 网络扩容 Description 给定一张有向图,每条边都有一个容量C和一个扩容费用W.这里扩容费用是指将容量扩大1所需的费用.求: 1. 在不 ...

  10. bzoj1834: [ZJOI2010]network 网络扩容

    努力看了很久样例一直过不了...然后各种输出中间过程啊巴拉巴拉弄了1h,没办法了...然后突然想到啊原来的边可以用啊为什么不用...于是A了...感人肺腑 #include<cstdio> ...

随机推荐

  1. javascript Math.pow 函数 详解 【附】年均增长率计算

    语法 Math.pow(x,y) 定义和用法 pow() 方法可返回 x 的 y 次幂的值. 处理简单数学问题 6的4次方等于1296,记作:64=1296; 求值: Math.pow(6,4)=12 ...

  2. JavaScript中的二分法插入算法

    算法主体部分 var OnlineUser = { //list : 待查找的数组 //key : 待插入的值 //order : 数组的顺序 1:从小到大 0:从大到小 //start : 开始查找 ...

  3. leetcode_sql_3,181,182,183

    181. Employees Earning More Than Their Managers The Employee table holds all employees including the ...

  4. Window Handle介绍

    HANDLE(句柄)是Windows操作系统中的一个概念.在Windows程序中,有各种各样的资源(窗口.图标.光标等),系统在创建这些资源时会为它们分配内存,并返回标示这些资源的标示号,即句柄.句柄 ...

  5. Doxygen详细介绍

    1 序言 为代码写注释一直是大多数程序员有些困扰的事情.当前程序员都能接受为了程序的可维护性.可读性编码的同时写注释的说法,但对哪些地方应该写注释,注释如何写,写多少等这些问题,很多程序员仍然没有答案 ...

  6. openfaas 架构介绍

     此为官方介绍   Overview of OpenFaaS Function Watchdog You can make any Docker image into a serverless fun ...

  7. wordpress改不了固定连接的解决办法

    经常遇到更改了固定连接刷新没效果>>>>>>>废话不多说直接上步骤,有图有真相. 1,ftp删除根目录的这个文件夹 2,进入wp后台设置-固定连接—自定义结构 ...

  8. JMeter启动时显示Could not open/create prefs root node Software\JavaSoft\Prefs at root 0X80000002

    在windows 7上启动jmeter时,提示错误: Java.util.prefs.WindowsPreferences <init> WARNING: Could not open/c ...

  9. 从JVM的角度解析String

    1. 字符串生成过程 我们都知道String s = "hello java";会将“hello java”放入字符串常量池,但是从jvm的角度来看字符串和三个常量池有关,clas ...

  10. 如何设计并使用FireMonkeyStyle

    如何设计并使用FireMonkeyStyle FireMonkey使用Style来控制控件的显示方式. 每个控件都有一个StyleLookup属性,FireMonkey就是通过控件的这个属性来在当前窗 ...