網路流 Edmons Karp 演算法講解

2022-03-15 15:17:27 字數 1936 閱讀 7564

網路流ek演算法

資料結構:佇列

主要操作:廣搜 記錄路徑 更新

能解決的問題:最大流(最小割)

複雜度:o(mv)v指最大容量,m指邊數。

新名詞:

1.增廣路:從源點source到tink的一條簡單路,如果路上的每條邊(u,v)的可改進量均大於0,則稱這條路為一條增廣路。

增廣路定理:網路達到最大流量當且僅當不存在增廣路。

增廣路演算法:從乙個可行流開始不斷的尋找可增廣路,然後沿著它增廣,直到它不存在。

2.反向弧:如果有一條弧(u,v),那麼再進行網路流演算法時,要對它建立反向弧(v,u),反向弧的容量為0,與正向弧相反,正向弧減少容量時,反向弧增加容量。建立反向弧能更多的增廣,使網路流演算法正確。(無法給出證明)

3.可行弧:在ek演算法中指可從u到v增加流量(也就是容量不為0)。

4.可行路:從源點source到tink的有可行弧構成的路徑叫做可行路。

具體操作:

1.建立網路(正向弧+反向弧)

2.從源點出發,廣搜一條最短可行路(即最先到達匯點tink的那條路),每次到達乙個點用pre陣列記錄是由那條邊過來的(為後面減小流量做準備)

3.到達匯點tink時,按照pre陣列記錄的,從可行路中找一條容量最小的進行容量減少。即找到了一條割邊。

4.重複操作2.3

,直到無法到達匯點,演算法結束,即找到了最大流,演算法結束。

4.2.1 純網路流演算法,可用來試ek的正確性,但ek只能拿50分!

1 #include2 #include3 #include4 #include5

using

namespace

std;67

#define inf 1000000 89

struct

edge10;

1314 edge map[200

];15

int que[20000

];16

bool b[500];//

用b陣列記錄是否入隊,可以防止重複入隊,因為有反向弧和環!!

17int

source,tink,n,m,tot,ans,head,tail;

18int first[500

];19

int pre[500

];20

21int fmin(int x ,int

y)22

2627

void build(int x ,int y ,int

c)28

4445

void

init()

4656 source=n+1; tink=n+2;//

手動建立源點和匯點,看題目要求!

57 build(source,1

,inf);

58build(n,tink,inf);59}

6061

bool

bfs()

6280 t=map[t].next;81}

82 head++;

83 b[x]=false;84

}

85return

false;86

}8788void

updata()

8995

for (int p=pre[tink];p!=-1;p=pre[map[p].x])//

更新容量過程

96100 ans+=min;

101}

102103

void

ek()

104110 printf("

%d\n

",ans);

111}

112113

intmain()

114

網路流演算法

問題描述 如圖4 1所示是聯結某產品地v1和銷售地v4的交通網,每一弧 vi,vj 代表從vi到vj的運輸線,產品經這條弧由vi輸送到vj,弧旁的數表示這條運輸線的最大通過能力。產品經過交通網從v1到v4。現在要求制定乙個運輸方案使從v1到v4的產品數量最多。圖 4 1 圖 4 2 一 基本概念及相...

網路流演算法

ek演算法模板 演算法複雜度 n m m n為點數,m為邊數 源點 1,匯點 n。const int maxn 310,inf 0x7fffffff int pre maxn mat maxn maxn bool vis maxn int n,m int augment else q.push ba...

網路流演算法

網路流演算法 網路流演算法用於解決從源點到匯點最大流的問題。edmonds karp演算法 演算法主要思想 每次bfs找到一條從源點到匯點的最少路徑數的可行路徑,同時把這條路徑塞滿,這條路上的最小容量即為這條路徑的流量。然後將這條路徑的正向邊刪除,增加一條容量相同的反向邊,當bfs無法進行下去的時候...