模板 最小費用最大流

2022-05-13 07:06:55 字數 1844 閱讀 7389

傳送門:qaqqaq

因為要在最大流的情況下,保證最小費用,所以我們在增廣時就用spfa跑乙個最短路進行增廣,雖然這個路徑可能不在最大流中,但殘量網路可以保證我們這個「可以反悔的貪心」不會出錯~

具體寫法:spfa+ek

**:

#include#define mk make_pair

using

namespace

std;

typedef pair

pii;

const

int inf=(int

)2e9;

const

int n=1020*50

;int

n,m,s,t;

int first[n*2],nxt[n*4],point[n*4],cost[n*4],flow[n*4],e=0

;void add(int x,int y,int z,int

c)void add_edge(int x,int y,int z,int

c)int

dis[n],inq[n],pre_point[n],f[n],pre_edge[n];

void

init_spfa()

queue

q;bool

spfa()}}

}return pre_point[t]!=-1;}

pii solve()

}return

mk(max_flow,min_cost);

}void

init()

}int

main()

view code

再來一道題:

傳送門:qaqqaq

題意:有$n$個盒子(1<=$n$<=1000)圍成乙個圈,每個盒子有$a_$個球,所有盒子的球的總數小於等於$n$.每一次移動,可以把乙個球移動到它的乙個相鄰的盒子內.

現在要使得每個盒子的球數$<=1$,求最少的移動次數

思路:直接說建圖吧(網路流主要就是難在建圖)

我們造乙個源點,乙個匯點,源點和每乙個點連一條容量為$a_$,費用為$0$的邊,匯點和每乙個點連一條容量為$1$,費用為$0$的邊,對於中間的點,我們對於它和它左右兩點各連一條容量為$inf$,費用為$1$的邊。

這樣我們跑一遍最小費用最大流即可(即在總流量為$sumball$的情況下,費用最小)

**:

#include#define mk make_pair

using

namespace

std;

typedef pair

pii;

const

int inf=(int

)2e9;

const

int n=100020;

intn,m,s,t;

int first[n*2],nxt[n*4],point[n*4],cost[n*4],flow[n*4],e=0

;void add(int x,int y,int z,int

c)void add_edge(int x,int y,int z,intc)

intdis[n],inq[n],pre_point[n],f[n],pre_edge[n];

void

init_spfa()

queue

q;bool

spfa()}}

}return pre_point[t]!=-1;}

intsolve()

}return

min_cost;}

inta[n];

void

init()}

intmain()

view code

最小費用最大流模板

const int n 1010 點 const int m 2 10010 邊 const int inf 1000000000 struct nodee m int next1 m point n dis n q n pre n ne ne為已新增的邊數,next,point為鄰接表,dis為花...

最小費用最大流模板

一 最小費用最大流的模型 在保證流量最大的前提下,所需的費用最小,這就是最小費用最大流問題 帶有費用的網路流圖 g v,e,c,w v 頂點 e 弧 c 弧的容量 w 單位流量費用。任意的弧對應非負的容量c i,j 和單位流量費用w i,j 滿足 流量f是g的最大流。在f是g的最大流的前提下,流的費...

最小費用最大流 模板

因為含有負權邊,所以使用spfa進行增廣。指定流量的最小費用流可以初始化乙個f,然後每次一直迴圈到f 0為止。函式返回的是最大流,當然經過少量修改可以返回最小費用,利用最小流量乘以相應的費用即可。prevv記錄父節點,preve記錄當前節點對應父節點的第幾條邊。const int inf 0x3ff...