О.О.П / ооп / 4_кол / К курсовой / Методи побудови алгоритмів та їх аналіз / 62_201
.PDFЗалишається тільки підбити підсумок виконання дій протягом цієї ітерації:
-знайдено додатковий варіант проходження мережі, тобто ще один доповнюючий шлях (1,2), (2,5), (5,6);
-при цьому значення максимального потоку збільшене на 5 одиниць (мал. 88, б).
|
[1,5] |
[2,5] |
ГІГ)-5(20)-ЦІГ) 10+5=15 |
|
|||
•с &' |
0(5) |
TS0j 0(3) |
-^ЇЧ°J °<г3>%•9М>. |
г |
|||
|
( З ) - 0(5) - * - ( 4 j |
|
|
|
-ОГ' |
|
|
|
|
|
|
|
|
||
|
[1,30] |
[3,5] |
1. |
2, |
52 |
6 |
|
|
2і |
3j 5J4g 6, |
|
||||
а) |
б) |
|
|
|
|
Мал. 88
Можна констатувати факт, що на завершення роботи другої ітерації до вершини-стоку потрапило вже 15 одиниць води.
Третя ітерація
Після двох виконаних кроків не будемо детально зупиня тися на третьому. Розглядаючи малюнок 88, б, визначимо послідовність ребер, якими можна пройти від витоку до стоку, збільшивши потік. Починаючи з вершини 1 з міткою [0, °о]; переходимо лише до вершини 3, помічаючи її міткою [1,30], оскільки по ребру (1,2) йде максимально можливий потік і вер шина 2 вже недосяжна. З вершини 3 можна перейти до вер шин 2 і 4. Позначаємо їх відповідно мітками [3,5], оскільки вони ще не розглядалися у даній ітерації і саме значеннями 5 визначені пропускні спроможності ребер (3,2) і (3,4). Наступ ний хід у вершину 2. З неї можна перейти лише до вершини 5: ребро (2,4) повністю насичене і перехід до вершини 4 неможли вий. Скільки води можна передати ще ребром (2,5)? Пропускна спроможність ребра дає змогу додати ще 15 одиниць, але у вер шину 2 прийшло лише 5, тому більше немає звідки взяти. Отже, обмежимося цим значенням і поставимо мітку [2,5] біля вершини 5. Далі у нашій послідовності іде вершина 4, яку ми побачили з вершини 3. Однак з неї вершини 6 не видно, оскіль ки ребро (4,6) насичене. Після вершини 4 у послідовності іде вершина 5. Переходимо до неї і можемо побачити вершину 6, яка є стоком. Резерв ребра (5,6) становить 7 одиниць води, але передати з вершини 5 можемо лише 5 одиниць. Зробимо це, поставивши мітку [5,5] біля вершини 6 (мал. 89, а).
142
|
[3,5] |
|
|
[2,5] |
|
(2)-10(20)*/5\ |
15+5=20 |
||||||
|
|
|
|
|
|
|
|
||||||
|
А-5(20)*Л |
|
-*Tv |
|
г* |
||||||||
|
|
|
|
|
|
|
|
|
|||||
|
&' |
|
|
|
|
|
*Ш ®* |
|
|
® |
^ |
J® |
|
Щ^ |
0(5) |
\ |
|
0(3) |
|
5(5) |
|||||||
а) |
1о |
3, |
23 |
43 |
52 |
65 |
|
10 |
3j |
23 |
52 |
65 |
|
б) |
|
|
|
|
|
|
Мал. 89
Черговий прохід мережею завершено, і нам вдалося проштовх нути доповнюючим шляхом (1,3), (3,2), (2,5), (5,6) ще 5 одиниць води. Тепер потік мережею становить 20 одиниць (мал. 89, б).
Четверта ітерація
Поки що не можна вважати процес пошуку максимального потоку в мережі завершеним, оскільки всі пройдені ітерації за вершуються вдало: вершина-стік досягається і значення мак симального потоку в мережі вдається збільшити.
Розглянувши поточний стан мережі, зображений на малюнку 89, б, можемо зробити висновок, що частина ребер вже повністю насичена, а деякі ребра ще мають перспективу бути донасиченими. До них відносяться ребра (1,3), (2,5), (3,4), (5,4), (5,6). Спробуємо побудувати новий доповнюючий шлях, використавши ці ребра.
Почнемо, як завжди, з вершини 1, помітивши її тра диційною міткою [0, °°] (мал. 90, о). З неї можна перейти лише до вершини 3, передавши туди 25 одиниць резервної води і по значивши міткою [1,25] (мал. 90, б).
Далі перейдемо до вершини 3 і побачимо лише вершину 4, куди можна передати, зважаючи на пропускну спроможність
|
(І)-10(20)-(5 |
(2)-іо(2"о» |
5 |
|
*«Гї\ |
;©« ^ 5(5)\ \% |
0(3) ;© |
ф ґ |
5(5) % 0(3) |
||
|
|
[1,25] |
[3,5] |
а) |
|
1о З, |
|
|
б) |
|
Мал. 90
143
ребра (3,4), лише 5 одиниць води з 25 можливих. Підтвердимо цей факт міткою [3,5] біля вершини 4 (мал. 91, а). А от куди йти далі? Дуже хотілося б потрапити у вершину 2, оскільки саме звідти можна перейти до вершини 6, але як там опинитися? Поставимо собі слушне запитання: а чи вірно ми розподілили воду в кожній вершині мережі? Проаналізувавши сумарні по токи води, що входять у кожну вершину і виходять з неї, зазначимо, що ці значення збігаються. Цей факт відомий з ви значення мережі: вода ззовні у вершини не поступає, тому скільки до них втікає ребрами, що входять, стільки само і витікає ребрами, що виходять. У вершинах 2 і 4 цей основний принцип мережі справджується.
Уважно розглянувши досліджувану мережу, можна поміти ти, що є можливість розподілити потік об'ємом 20 одиниць, який приходить у вершину 2, далі у вершини 4 і 5 інакше, ніж це вийшло у результаті виконання попередніх ітерацій. На приклад, ребра (2,5) і (5,6) дають змогу пропустити більше ніж 10 одиниць води, тим самим на це значення зменшиться потік через ребра (2,4) і (4,5). Це, у свою чергу, дасть можливість донаситити ребро (4,6), подавши воду у вершину 4 ребром (3,4). Отже, вирішення проблеми знайдено і можна буде виконати ще одну ітерацію.
Сформулюємо задачу, що виникла, мовою графів так: повер немо частину потоку, що попередньо спрямований ребром (2,4), у зворотному напрямі. Насправді, потік не повертається назад, а лише його поточне значення зменшується на деяке значення.
Введемо фіктивне ребро (4,2), позначене на малюнку 91, б пунктирною лінією, що називається зворотним ребром. Усі ре ально існуючі у мережі ребра називаються прямими. Ще раз за уважимо, що насправді ребра (4,2) у мережі не існує. Уведення його до мережі означатиме лише те, що попередньо спрямова ний потік з вершини 2 у вершину 4 зі значенням 10 буде змен шено на деяке значення, що не перевищує насиченості прямого ребра. Цей факт зрозумілий, оскільки не можна прибрати з ребра (2,4) більше води, ніж там уже є. Який же потік можна передати зворотним ребром (4,2) у вершину 2? Стільки, скіль ки прийшло у вершину 4, тобто 5 одиниць. Це можливо зроби ти, оскільки пропускна спроможність зворотного ребра (4,2) така сама, як і прямого (2,4): труба ж одна і та сама! Поставимо мітку [4, -5] біля вершини 2, де на цей раз значення потоку, що передається у неї зворотним ребром з вершини 4, позначимо від'ємним числом - 5 . У послідовність вершин допишемо види му вершину 2 з індексом -4, відмічаючи цим, що сюди при йшли саме зворотним ребром (мал. 91, б).
144
|
|
(2>к10(20) *Ч 5 |
|
[4,-5] |
|
|
|
|
|
|
|
||
|
Хї\ |
|
|
(2VlO(20)-^(T) |
||
|
|
|
|
|
||
|
|
5(5) |
% , 0(3) |
|
|
|
[0,»] % |
J |
..\L |
|
|
SST |
|
|
|
|
|
|||
|
|
|
»Л |
v ^ |
||
|
|
[1,25] |
[3,5] |
|
<ф-0(5) |
jjp |
|
|
|
[1,25] |
[3,5] |
||
|
|
|
|
|
||
|
|
lo 3, |
4 |
|
3, |
|
a) |
|
u |
|
6) |
|
|
|
|
|
|
|||
|
|
|
|
|
|
|
|
|
|
Мал. |
91 |
|
|
Отже, вихід знайдено і процес попіуку доповнюючого шляху з витоку до стоку, що можливо збільшить шуканий потік, роз блоковано. Дивимося з вершини 2 і бачимо нову вершину 5. У неї можна передати ще 5 одиниць води, які віртуально надійшли з вершини 4, а реально зекономлені у вершині 2. Зауважимо, що резерв ребра (2,5) становить на даний момент 10 одиниць води, однак у вершину 5 може прийти лише 5 оди ниць, які додатково подаються з вершини 2. Ставимо мітку [2,5] біля вершини 5 і дописуємо цю вершину у послідовність (мал. 92, а).
Тепер уже з вершини 5 видно стокову вершину 6. Вона буде позначена міткою [5,2], оскільки резерв ребра (5,6) обмежений величиною потоку 2. Таким чином, у вершину 6 надійшло ще 2 одиниці води (мал. 92, б).
|
[4,-5] |
[2,5] |
|
|
|
|
|
|
|
-Щ20)*^5Х |
|
|
|
1^-10(20) - ф ^ |
|
||
|
*••%Т Х |
|
,.« і'Ч, І '"• |
|||||
|
5(5) |
Sh-:<Z 0(3) |
;© |
|
|
5(5) |
V 3 - 0(3) |
J |
[0,оо] |
> , |
|
[0,оо] % |
5(5) |
||||
|
|
\ 1 |
.V*№] |
|||||
|
'°К |
|
|
|
|
|
||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
- 0 ( 5 ) ^ ^ ґ |
|
|
[1,25] |
[3,5] |
|
|
|
[1,25] |
[3,5] |
|
|
|
|
|
І |
|
|||
а) |
1. З, 43 2_4 5: |
|
б) |
|
1, 3, 43 2_4 52 6 |
|
||
|
|
¥ |
|
|
|
15 |
|
|
|
|
Мал. |
92 |
|
|
|
||
|
|
|
|
|
|
|
Сумарна кількість води, яку нам вдалося пропустити мере жею, виконавши чотири ітерації, становить 22. На малюнку 93, а виділеними ребрами зображено отриманий доповнюючий шлях від витоку до стоку, що дає змогу проштовхнути мере жею ще 2 одиниці води.
Логічно було б прибрати уявне ребро (4,2) з мережі, оскіль ки воно вже виконало свою функцію. Для цього досить просу - мувати значення потоків, що рухаються прямим ребром (2,4)
145
ребра (3,4), лише 5 одиниць води з 25 можливих. Підтвердимо цей факт міткою [3,5] біля вершини 4 (мал. 91, а). А от куди йти далі? Дуже хотілося б потрапити у вершину 2, оскільки саме звідти можна перейти до вершини 6, але як там опинитися? Поставимо собі слушне запитання: а чи вірно ми розподілили воду в кожній вершині мережі? Проаналізувавши сумарні по токи води, що входять у кожну вершину і виходять з неї, зазначимо, що ці значення збігаються. Цей факт відомий з ви значення мережі: вода ззовні у вершини не поступає, тому скільки до них втікає ребрами, що входять, стільки само і витікає ребрами, що виходять. У вершинах 2 і 4 цей основний принцип мережі справджується.
Уважно розглянувши досліджувану мережу, можна поміти ти, що є можливість розподілити потік об'ємом 20 одиниць, який приходить у вершину 2, далі у вершини 4 і 5 інакше, ніж це вийшло у результаті виконання попередніх ітерацій. На приклад, ребра (2,5) і (5,6) дають змогу пропустити більше ніж 10 одиниць води, тим самим на це значення зменшиться потік через ребра (2,4) і (4,5). Це, у свою чергу, дасть можливість донаситити ребро (4,6), подавши воду у вершину 4 ребром (3,4). Отже, вирішення проблеми знайдено і можна буде виконати ще одну ітерацію.
Сформулюємо задачу, що виникла, мовою графів так: повер немо частину потоку, що попередньо спрямований ребром (2,4), у зворотному напрямі. Насправді, потік не повертається назад, а лише його поточне значення зменшується на деяке значення.
Введемо фіктивне ребро (4,2), позначене на малюнку 91, б пунктирною лінією, що називається зворотним ребром. Усі ре ально існуючі у мережі ребра називаються прямими. Ще раз за уважимо, що насправді ребра (4,2) у мережі не існує. Уведення його до мережі означатиме лише те, що попередньо спрямова ний потік з вершини 2 у вершину 4 зі значенням 10 буде змен шено на деяке значення, що не перевищує насиченості прямого ребра. Цей факт зрозумілий, оскільки не можна прибрати з ребра (2,4) більше води, ніж там уже є. Який же потік можна передати зворотним ребром (4,2) у вершину 2? Стільки, скіль ки прийшло у вершину 4, тобто 5 одиниць. Це можливо зроби ти, оскільки пропускна спроможність зворотного ребра (4,2) така сама, як і прямого (2,4): труба ж одна і та сама! Поставимо мітку [4, -5] біля вершини 2, де на цей раз значення потоку, що передається у неї зворотним ребром з вершини 4, позначимо від'ємним числом -5. У послідовність вершин допишемо види му вершину 2 з індексом -4, відмічаючи цим, що сюди при йшли саме зворотним ребром (мал. 91, б).
144
(1Г)-10(20)*-С5 |
[4,-5] |
|
|
|
|
[1,25] |
|
[3,5] |
|
1. |
З, |
4 |
З, |
4 3 |
2_4 |
|
а) |
S |
б) |
||||
|
тг |
|
||||
|
|
Мал. 91 |
|
|
Отже, вихід знайдено і процес пошуку доповнюючого шляху з витоку до стоку, що можливо збільшить шуканий потік, роз блоковано. Дивимося з вершини 2 і бачимо нову вершину 5. У неї можна передати ще 5 одиниць води, які віртуально надійшли з вершини 4, а реально зекономлені у вершині 2. Зауважимо, що резерв ребра (2,5) становить на даний момент 10 одиниць води, однак у вершину 5 може прийти лише 5 оди ниць, які додатково подаються з вершини 2. Ставимо мітку [2,5] біля вершини 5 і дописуємо цю вершину у послідовність (мал. 92, а).
Тепер уже з вершини 5 видно стокову вершину 6. Вона буде позначена міткою [5,2], оскільки резерв ребра (5,6) обмежений величиною потоку 2. Таким чином, у вершину 6 надійшло ще 2 одиниці води (мал. 92, б).
|
[4,-5] |
|
[2,5] |
|
|
[4,-5] |
[2,5] |
|
-10(20) н |
|
|
|
|
|
|
|
|
•(&, |
|
|
|
|
|
|
|
|
%, |
|
|
|
|
|
5(5) |
%-fo, |
0(3) |
|
|
5(5) |
V 9 0(3) |
|
с %Л |
4 \i>v |
[0,оо] |
4ач». |
|
•%L#лУП^] |
|
|
|
|
|
|
|
-(К5)^ЩГ |
|
|
[1,25] |
|
[3,5] |
|
|
[1,25] |
[3,5] |
|
|
|
|
і~ |
|||
а) |
1<> 3, |
4 3 2_4 |
5 2 |
б) |
1.13,14,12^5,16, |
||
|
|
т |
|
Мал. 92 |
|
|
|
Сумарна кількість води, яку нам вдалося пропустити мере жею, виконавши чотири ітерації, становить 22. На малюнку 93, а виділеними ребрами зображено отриманий доповнюючий пілях від витоку до стоку, що дає змогу проштовхнути мере жею ще 2 одиниці води.
Логічно було б прибрати уявне ребро (4,2) з мережі, оскіль ки воно вже виконало свою функцію. Для цього досить просумувати значення потоків, що рухаються прямим ребром (2,4)
145
(Т)-12(20)*/5І 20+2=22 |
(І}-12(20)*/5І 20+2=22 |
|
|
|
*<3«г |
|
5(5) |
% 0(3) |
\3)-2(5)-^4X |
(З |
.•** |
5)-К 4! |
||
10 З, 4.2J5J6, |
|
|
а) |
б) |
|
Мал. 93
та зворотним (4,2), і отримати такий результат: ребро (2,4) у мережі насичене на 8 одиниць води з 10 можливих (мал. 93, б).
П'ята ітерація
У стоковій вершині 6 отримано очікувані 22 одиниці води. Однак необхідно виконати ще одну ітерацію для того, щоб пе реконатися, що немає більше доповнюючого шляху від вито ку 1 до стоку 6, який би збільшив потік у мережі і зміг би про штовхнути ще одну порцію води.
Почнемо рух з вершини 1. З неї можна пройти лише до вер шини 3, оскільки резерв ребра (1,3) становить 23 одиниці. З вершини 3 можна рухатися лише у напрямі вершини 4 (ре зерв ребра (3,4) - 3 одиниці). З вершини 4 можна перейти до вершини 2 зворотним ребром (4,2), насиченість якого дорівнює від'ємному значенню насиченості прямого ребра (2,4), тобто - 8, і пропустити ті самі 3 одиниці води, що надійшли у вершину 4. Перейшовши у вершину 2, рухаємося далі у вершину 5: резерв ребра (2,5) дає змогу це зробити. І на цьому наш рух припи няється, оскільки з вершини 5 можна перейти лише у верши ну 6, однак ребро (5,6) вже максимально насичене (мал. 94, а).
Нам не вдалося побудувати ще один доповнюючий шлях від витоку до стоку, який би дав змогу перегнати додаткову порцію
[4,-3] |
[2,3] |
(2)-12(20)*(5\ |
22 |
(2)-12(20)*/5^ |
>^\2А |
||
гх^ |
Н І |
v-л dx вд % |
°<з>:© |
®Ч Т" чТ х® N1 VX |
|||
°ЧЛ |
Ух* |
©-2(5)^(4) |
|
[1,23] |
[3,3] |
|
|
а) lo 3 t 43 2.4 5 |
б) |
|
Мал. 94 |
. |
|
146
води. Це означає, що значення максимального потоку 22 отри мано і визначені насиченості кожного ребра мережі (мал. 94, б).
Аналізуючи отриманий результат, слід відзначити, що у ме режі залишилося тільки одне незадіяне порожнє ребро (5,4). Слушним є запитання: а чому під час виконання п'ятої ітерації не була здійснена спроба по ньому пустити воду в зворотному напрямі? Відповідь буде такою: потік можна пускати у зворот ному напрямі тільки тоді, коли вже існує потік цим ребром у прямому напрямі. Така відповідь пояснюється тим, що наяв ність зворотного напряму потоку відповідає зменшенню потоку в прямому напрямі, а що ж можна зменшити, якщо потоку зовсім немає.
Сформулюємо алгоритм метода Форда-Фалкерсона.
1.Почати перегляд вершин мережі з вершини-витоку s і визначити її як поточну відвідану.
2.Визначити вершини мережі, які можна побачити з поточ ної відвіданої вершини.
3.Якщо такі вершини є і серед них відсутня верпіина-стік t, то надати їм статус «побачених» і позначити відповідними міт ками. У протилежному разі перейти до п. 6.
4.Перейти до першої з послідовності «побачених» вершин і визначити її статус як відвіданої.
5.Перейти до п. 2.
6.Якщо статус «побаченої» вершини отримала вершинастік, то збільшити потік у мережі на значення потоку, що наді йшов до вершини t, і додати це значення до значень поточної насиченості всіх ребер, з яких складається визначений допов нюючий шлях від вершини-витоку s до вершини-стоку t. Пе рейти до п. 1.
7.Якщо у послідовності «побачених» вершин відсутня вер- шина-стік t і до послідовності «побачених» вершин немає мож ливості приписати жодної нової вершини, то значення макси мального потоку в мережі визначається значенням потоку, що отриманий у вершині-стоку t.
8.Завершити алгоритм.
Перейдемо безпосередньо до реалізації описаного алгорит му мовою програмування. Відмінність програми від алгоритму подекуди буває досить значною. Метод, який лежить в основі й алгоритму, і програми, один і той самий, а от для безпосе редньої реалізації алгоритму у вигляді програми необхідно ввести додаткові змінні, умови аналізу тих чи інших поточних ситуацій.
Вхідна інформація про задану мережу міститиметься у дво вимірному масиві С[і, j], а інформація про поточний стан наси ченості ребер - у двовимірному масиві F[i, j]. Різниця між від-
147
повідними елементами цих масивів свідчитиме про резерв на сиченості кожного ребра.
Послідовність відвіданих та «побачених» вершин являє собою структуру даних «черга», і для її організації виділяється одновимірний масив q. Оскільки кожна «побачена» вершина мережі отримує мітку у вигляді номера вершини, з якої її було побаче но, і величини потоку, який може у неї прийти, то для збере ження цієї інформації організовано масив Ibl типу record, перше поле якого містить номер вершини-предкаргеи, а друге - зна чення потоку flow. Як ми бачили у раніше розглянутому прикла ді (можна звернути увагу на два останні кроки п'ятої ітерації), значення змінної flow обирається як мінімальне між тим пото ком, який ще можна пропустити ребром (u,u) (C[u,u] - F[u,v]), і тим, що прийшов у вершину и.
Сенс усіх досі визначених змінних повністю відповідає опи саному вище алгоритму. Тепер розглянемо питання фіксації зворотних, тобто віртуальних, ребер. У прикладі зворотне ребро
|
1 |
2 |
3 |
4 |
|
|
5 |
6 |
|
|
|
1 |
2 |
3 |
4 |
|
|
5 |
6 |
|||||||||||
1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
0 |
10 |
|
0 |
0 |
|
|
0 |
0 |
|
0 |
|
15 |
|
0 |
0 |
|
|
0 |
0 |
|||||||||||
2 |
|
|
|
|
|
|
|
|
|
|
|
|
|
2 |
|
|
|
|
|
|
|
|
|
|
|
|||||
-10 |
0 |
0 |
10 |
|
|
0 |
0 |
|
-15 |
0 |
0 |
10 |
5 |
0 |
||||||||||||||||
3 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
0 |
0 |
|
0 |
0 |
|
|
0 |
0 |
|
0 |
|
0 |
|
0 |
0 |
|
|
0 |
0 |
|||||||||||
4 |
|
|
|
|
|
|
|
|
|
|
|
|
4 |
|
|
|
|
|
|
|
|
|
|
|
|
|||||
0 |
-10 |
0 |
0 |
0 |
10 |
|
0 |
|
-10 |
0 |
0 |
0 |
10 |
|||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
5 |
|
|
|
|
|
|
|
|
|
|
|
|
|||||
5 |
0 |
0 |
0 |
0 |
0 |
0 |
|
0 |
|
-5 |
0 |
0 |
0 |
5 |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
6 |
|
|
|
|
|
|
|
|
|
|
|
|
|||||
6 |
0 |
0 |
0 |
-10 |
0 |
0 |
|
0 |
|
0 |
0 |
-10 |
-5 |
0 |
||||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 ітерація |
|
|
|
|
|
|
|
|
|
|
2 ітерація |
|
|
|
||||||||||||
|
|
2 |
3 |
4 |
|
|
5 |
|
|
|
|
|
1 |
2 |
3 |
4 |
|
|
5 |
|
|
|||||||||
|
0 |
|
15 |
|
|
5 |
0 |
|
|
0 |
|
0 |
|
|
1 |
0 |
|
15 |
|
7 |
|
0 |
|
|
0 |
|
0 |
|||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||||||||
|
-15 |
0 |
-5 |
10 |
10 |
0 |
|
|
2 |
-15 |
0 |
-5 |
8 |
12 |
0 |
|||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
||||||||||
|
-5 |
5 |
0 |
0 |
0 |
0 |
|
|
З |
-7 |
5 |
0 |
2 |
0 |
0 |
|||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||||||||
|
0 |
-10 |
0 |
0 |
0 |
10 |
|
|
4 |
-8 |
-2 |
0 |
0 |
0 |
10 |
|||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||||||||
|
0 |
-10 |
0 |
0 |
0 |
10 |
|
|
5 |
0 |
-12 |
0 |
0 |
0 |
12 |
|||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|||||||||||
|
0 |
0 |
0 |
-10 |
-10 |
0 |
|
|
6 |
0 |
0 |
0 |
-10 |
-12 |
0 |
|||||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
||
|
|
|
|
|
|
З ітерація |
|
|
|
Мал. 95 |
|
|
|
|
4 ітерація |
|
|
|
||||||||||||
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
148
введено у той момент, коли виникла безвихідна ситуація: виявилася недосяжною вершина-стік. Пошук вершини на де якому етапі виконання програми, в якій можна було б перероз поділити потік, - зайва трата часу. Тому, оскільки наперед невідомо, для якого прямого ребра з'явиться потреба у вико ристанні його зворотного близнюка, будемо про всяк випадок зберігати зворотне значення для кожного ребра, для якого об числюється значення потоку. Тобто для прямого ребра (и, v) зберігатимемо інформацію F[u, v], а для відповідного йому зво ротного ребра (и, и) - від'ємне значення -F[u, v]. На малюн ку 95 зображено стани масиву F після виконання кожної з чо тирьох результативних ітерацій.
Таким чином, шукаючи з поточної відвіданої вершини і наступну видиму вершину ;', розглядатимемо як прямі ребра, для яких насиченість ще не перевищила пропускної спромож ності С[і, j] - F[i, j] > 0, так і зворотні з ненульовими значення ми, що свідчитиме про існування відповідного прямого ребра. Оскільки зворотні ребра у масиві С не визначені, тобто С[і, j] = 0 (їх у мережі немає), а у масиві F вони визначені від'ємними числами F[i,j] < 0, то вираз С[і, j] - F[i, j] так само буде додат ним: С[і, j] - F[i, j] > 0. Отже, умова існування потоку ребром (і, j) однакова як для прямих, так і для зворотних ребер.
Підбиваючи підсумок усього вищесказаного, можна запро понувати такий компактний і зрозумілий запис алгоритму Форда-Фалкерсона:
Поки існує доповнюючий шлях з вершини-витоку до вершини-стоку, виконати:
визначити значення потоку у вершині-стоку flowt;
для кожного ребра (u,v) знайденого доповнюючого шляху виконати:
F[u,v] := F[u,v] + flowt; F[v,u] := -F[u,v] + flowt;
Удосконаленням методу Форда-Фалкерсона вважається використання алгоритму пошуку в ширину для визначення найкоротшого шляху від вершини-витоку до вершини-стоку, запропонований Едмондеоном і Карпом.
Пропонується такий можливий варіант реалізації процедури проходження мережею від витоку s до стоку t для пошуку до повнюючого шляху, який дасть можливість збільшити потік:
procedure marking(var new_flow: integer); begin
while (head < tail) and not flag do {Поки «голова» черги менша від «хвоста»}
b e g i n |
{і вершина стоку не досягнута, починаємо пошук} |
І v := 1; |
{існуючого ребра як в алгоритмі пошуку в ширину.} |
149