
































Studia grazie alle numerose risorse presenti su Docsity
Guadagna punti aiutando altri studenti oppure acquistali con un piano Premium
Prepara i tuoi esami
Studia grazie alle numerose risorse presenti su Docsity
Prepara i tuoi esami con i documenti condivisi da studenti come te su Docsity
Trova i documenti specifici per gli esami della tua università
Preparati con lezioni e prove svolte basate sui programmi universitari!
Rispondi a reali domande d’esame e scopri la tua preparazione
Riassumi i tuoi documenti, fagli domande, convertili in quiz e mappe concettuali
Studia con prove svolte, tesine e consigli utili
Togliti ogni dubbio leggendo le risposte alle domande fatte da altri studenti come te
Esplora i documenti più scaricati per gli argomenti di studio più popolari
Ottieni i punti per scaricare
Guadagna punti aiutando altri studenti oppure acquistali con un piano Premium
Domande+risposte dell'Esame "Ottimizzazione Combinatoria"
Tipologia: Prove d'esame
1 / 40
Questa pagina non è visibile nell’anteprima
Non perderti parti importanti!

































I problemi di OC sono particolari problemi di decisione, molto diffusi e di tipologie diverse. PROBLEMI DI DECISIONE: min [f(x): xЄ ] x = variabile di decisione; = insieme di possibili alternative; soluzione ottima : x* : f(x*) ≤ f(x) xЄ; soluzione ammissibile : ogni xЄ
Nonostante la varietà delle tipologie, i problemi di decisione hanno in comune il fatto che occorre scegliere tra un insieme di alternative, ben distinte e non mescolabili. Dato per effettuare la scelta abbiamo un criterio quantitativo: f(x): S -> R : funzione obiettivo, di solito la funzione più semplice che rappresenta bene il nostro criterio. I problemi di OC sono risolubili attraverso un approccio MODELLISTICO, ovvero si crea un modello del problema e si usano algoritmi già studiati. Un problema di OC ha la seguente struttura: Insieme di base B={b 1 ,..,bn} costituito da eventi elementari (es: progetto i a ttiva to, connessione j stabilita); Soluzione Ammissibile: indicata da un insieme S B; esso è costituito da un insieme da eventi elementari che rispettano le condizioni date; Insieme delle soluzioni ammissibili: ={S1,..Sn} P(B) e di cardinalità 2n; questo insieme ha cardinalità finita, ossia x* , punto ottimo, può essere individuato tramite un’enumerazione completa di => le componenti di ogni aspetto di un problema di decisione possono assumere un numero finito di valori. Allora avrò sempre un insieme finito di soluzioni Ogni elemento dell’insieme di base ha il suo COSTO (VANTAGGIO) ELEMENTARE che indichiamo con {ci }; Funzione di costo: C: S -> R che, nel caso lineare è c(S)= (^) i , ovvero associo ad ogni Si il costo dato dalla somma dei costi ci degli elementi i-esimi di B che lo definiscono. Vogliamo quindi trovare : min {c(S) : SЄ}
Ogni problema di OC con f.obiettivo lineare può essere scritto come PLO1. La corrispondenza riguarda il fatto che la soluzione ammissibile S può essere rappresentata tramite il vettore di incidenza xS. Il vettore di incidenza è un vettore colonna con tante righe quanti sono gli eventi elementari; per ognuno di questi avrò il vettore 0 se l’elemento B non è presente in S e il vettore 1 se l’elemento B è presente in S. Problema OC: - Funzione obiettivo c{S}
Problema PLO1: - Funzione obiettivo cTx;
Definiamo un esempio di pianificazione degli investimenti in cui abbiamo:
a 11 x 1 +a 21 x 2 +..+an1xn ≤ bj con xiЄ{0,1} i=1,..,n Possibilità offerte dal modello:
● xi ≤ [≥, =] xj → i può essere svolto solo se [è svol to se, è svol to se e solo se ] j viene svolto;
● xi+ xj ≤ 1 → solo uno tra i e j può essere svolto (ad es. se i e j sono copie dello stesso progetto con stessi flussi ma diversi inizi)
● xi = (1 - xj ) → i viene svolto se e solo x se non viene svolto j
● xi ≤ xh + xk + (1 - xj ) → i può essere svolto solo se h o k vengono svolti o j non viene svolto (almeno una delle 3 condiz.)
● xi ≤ ( xh + xk + (1 - xj )) /3 → i può essere svolto solo se h e k vengono svolti e j non viene svolto (tutte e 3)
● xi ≤ [≥, =] xj → i può essere svolto solo se [è svol to se, è svol to se e solo se ] j viene svolto;
● xi+ xj ≤ 1 → solo uno tra i e j può essere svolto: se i viene svolto, j non viene svolto, ma se i non viene svolto j può anche non essere svolto. (ad es. se i e j sono copie dello stesso progetto con stessi flussi ma diversi inizi);
Correttezza : applicato alla stessa istanza I restituisce sempre la stessa soluzione F(I); Efficienza : quantità di risorse impiegate dal calcolatore quali spazio e tempo. -Spazio: numero di bit necessari a memorizzare IЄ I e al calcolo restituisce la soluzione F(I) -Tempo: numero di passi (o iterazioni) necessarie per restituire una soluzione F(I) Il numero di passi (tempo) può essere calcolato con un modello idealizzato di calcolator e chiamato RAM , il quale esegue operazioni primitive su celle (parole) che contengono un numero costante di bit (32 o 64) ognuna delle quali richiede un passo. Il valore esatto dipende dalla dimensione dell’istanza “size(I)” e dalla specifica istanza. Ogni algoritmo ha una complessità C(size(I)) data dal numero di passi necessari per determinare la soluzione di una generica istanza di dimensione size(I). Dimensione size(I) : numero di celle necessarie a rappresentare i dati in ingresso (istanza I); Complessità size(I): per definirla potremmo considerare il valor medio del tempo di esecuzione su tutte le istanze di dimensione size(I). Consideriamo due casi estremo: Complessità nel caso peggiore W(size(I)) : è funzione di size(I) ed è il numero di passi necessari ad un algoritmo per determinare la soluzione della più difficile istanza di dimensione size(I). Complessità nel caso migliore B(size(I)) : è funzione di size(I) ed è il numero di passi necessari ad un algoritmo per determinare la soluzione della più facile istanza di dimensione size(I). Per considerare un’approssimazione più realistica e prudenziale , utilizzo la complessità nel caso peggiore, ovvero utilizzo un’approssimazione superiore (UPPER BOUND) g(size(I)) della funzione w(size(I)). Un algoritmo nel caso peggiore ha complessità θ(g(size(I)) se e solo se g(size(I)) è upperbound di W(size(I)). È possibile avere vari comportamenti di complessità, tra cui: Polinomiale: un algoritmo ha complessità polinomiale se la sua complessità nel caso peggiore è θ(size(I)k) con k= costante, ossia un polinomio. L’algoritmo polinomiale è efficiente (“good”) e risolubile e il valore di k è una misura dell’efficienza dell’algoritmo poiché più k è basso più è efficiente l’algoritmo. Esponenziale: un algoritmo ha complessità esponenziale se la sua co mplessità nel caso peggiore è limitata da un esponenziale, ma non da un polinomio, cioè cresce più velocemente di size(I)k^ per ogni k. L’algoritmo esponenziale non è efficiente (“bad”) perché non sempre giunge a una soluzione.
Per definire le classi di complessità utilizziamo un calcolatore chiamato MACCHINA DI TOURING, formata da un nastro (infinito, ogni cella contiene un simbolo), una testina (legge o scrive il nastro e si sposta rispetto a lui), un programma (per ogni stato e simbolo in input, una
regola che dice cosa fare) e uno stato (appartiene ad un insieme di possibili stati). Questa può essere: DETERMINISTICA: dato uno stato e un input esegue una determinata operazione NON DETERMINISTICA: dato uno stato e un input può eseguire una tra varie determinate operazioni. Quindi definiamo a seconda dell’andamento delle complessità, usando il modello della Macchina di Touring, le classi di complessità: Classe P : problemi risolubili in un tempo polinomiale su MdT deterministica Classe NP : problemi risolubili in un tempo polinomiale su MdT non determinist Classe ExpT : problemi risolubili in un tempo esponenziale su MdT determinist
La relazione tra queste due classi è di inclusione. Ma esistono incertezze. Sappiamo che P NP ma non sappiamo se P NP o P=NP e questo è uno dei problemi aperti da anni (millennium problems). I problemi di OC, PL01 ad esempio sono risolubili attualmente solo in tempo esponenziale (per cui difficili), ma lavorando con una MdT non deterministica (che non esiste nella realtà) potrebbero essere risolubili in un tempo polinomiale (e quindi diventare facili). La PL appartiene alla classe P, quindi risolvere un problema di PL è facile, mentre uno di OC o PL01 è difficile. Dato un problema, posso progettare diversi algoritmi per risolverlo ma non è detto che tutti abbiano la stessa complessità: alcuni potrebbero anche essere corretti ma poco efficienti. Allore la complessità di un problema è data da quella dell’algoritmo più facile per risolverlo. Un problema di si dice NP-hard se la sua complessità è >= di quella di qualsiasi altro problema, si dice NP completo se è in NP ed è NP-hard. Molti problemi di OC sono NP completi.
Dato un problema di PL01 : min{ cTx: xЄS} con S={xЄ {0,1}n^ : x rispetta alcune condizioni}, e dato il poliedro P={xЄRn^ : A∙x ≤ b}, cioè un poliedro con (AЄRmxn, bЄRm), allora P è una formulazione di S se e solo se P { 0,1 } n^ = S , ovvero se identifica tutti i punti (0,1) ammissibili del problema separandoli da quelli non ammissibili. Dello stesso problema di PL01 è possibile avere infinite formulazioni. → P è una FORMULAZIONE se e solo se: -contiene tutti i vettori di S -non contiene alcun vettore di {0,1}n^ – S
La formulazione ottima è la migliore tra quelle contenute in P, quella più stringente poiché passante per i vertici {1,0}n, cioè per i punti buoni. È definita come: con Ps=”involucro convesso”. Considerando la formulazione ottima, il “lower bound”, cioè il valore ottimo della PL risulta coincidente con il valore
con x^0 : soluzione ottima del rilassamento lineare x^0 Є ExT(Ps) = S → x^0 soluzione ottima di PL z* = LB(Ps)=cTx^0 → cTx^0 =z*≤ cTx xЄS
Non disponiamo di una descrizione di PS per ogni problema di PL01 ma possiamo considerare i rilassamenti di Ps: P={xЄRm^ : Dx ≤ d} è un poliedro corrispondente ad una formulazione di S ed è costituito da alcune famiglie di disequazioni del sistema Ax ≤ b (da Ps= xЄRn^ : Ax≤b} del problema di PL01). Quindi risolvere il problema di PL rispetto a P corrisponde a fare il rilassamento lineare di Ps; questo produce il lower bound di z* (poiché ciascun rilassamento produce un lower bound di z*).
In generale:
max cAxA+cBxB = min (^) - cAxA-cBxB con xЄS={ }
FORMULAZIONE NATURALE: xЄPN : dAxA + dBxB ≤ D xA ≤ 1, xB ≥ E’ una formulazione perché si verifica : PN Λ {1,0}^2 = S a) xЄS → xЄPN (S PN Λ {1,0}^2 ) b) xЄPN Λ {1,0}^2 → xЄS (PN Λ {1,0}^2 S)
FORMULAZIONE OTTIMA: max cAxA+cBxB = min (^) - cAxA-cBxB xєPS : xA+xB ≤ 1 (vincolo logico: uno solo dei sue progetti piò essere a ttiva to) xA ≤ 1 , xB ≥ 0
Esempio: Siano dati i progetti A e B sul singolo periodo; i vantaggi associati cA e cB sono: cA=2 e cB=9. Le risorse necessarie sono dA=8 e dB=11. Il vincolo è utilizzare risorse per un valore D≤ 15. FORMULAZIONE NATURALE min (^) - cAxA-cBxB → min(-2xA -9xB)
xЄPN : 8xA + 11xB ≤ 15 xA ≤ 1, xB ≥
FORMULAZIONE OTTIMA min(-2xA -9xB) xєPS : xA+xB ≤ 1 xA ≤ 1 , xB ≥ 0
Per dimostrare se la formulazione è ottima, per qualsiasi funzione obiettivo si può dimostrare uno dei seguenti punti: 1- Ogni disequazione del sistema Ax ≤ b è implicata dal sistema Dx ≤ d 2- Oppure che ogni argmin{cTx : xЄP} ЄS cЄRm 3- Oppure che ogni vertice di P ha componenti 0-1. In questo caso è necessario definire il concetto di unimodularità, ovvero di matrice uni modulare e totalmente uni modulare:
x^0 è un vertice di P={xЄRm: Ax ≤ b, x≥ 0n} se e solo se x^0 è una SBA (soluzione di base ammissibile). x^0 è una SBA se e solo se esiste una sottomatrice B(mxm) di A non singolare, cioè det(B)Ø 0
tale che, posto x= e A=(B N), abbiamo:
avendo scomposto x e A in una componente in base ad una fuori base, allora:
- scartando quelli dove quanto di meglio potrei ottenere (dato dal lower bound ) non è migliore di quanto già ho (ottimo corrente) - analizzando gli altri : aggiornando l’ottimo corrente nel caso di soluzioni ammissibili migliori o partizionando ulteriormente i sottoinsiemi non abbastanza facili
BOUNDING: consiste nel trovare il lower bound di un problema limitatamente a Pi, cercando un compromesso tra la velocità di calcolo e l’accuratezza del bound. (Più sottoproblemi elimino, più velocizzo la soluzione del problema complessivo) BRANCHING: rappresenta le tecniche utilizzate per generare i sottoproblemi Pi, cercando di avere Pi abbastanza semplici e di non averne troppi. Partendo dal Bounding (RILASSAMENTO LINEARE) si partiziona la formulazione P in sottoproblemi Pi; si eliminano i vincoli di interezza del sottoproblema Pi ottenendo un problema rilassato facilmente risolubile con il metodo del simplesso. Il minimo trovato sarà ≤ del minimo del problema non rilassato (intero). Trovato il lower bound di Pi l’accuratezza sarà tanto maggiore quanto più alta è la qualità di Pi. Esistono altre tecniche, oltre quella descritta, per individuare il lower bound. Tra queste: Rilassamento di altri vincoli difficili , ottenendo un sottoproblema più facile con insieme ammissibile più grande. Aumentando il numero di punti tra cui scegliere, il minimo di cTx non potrà che diminuire o restare uguale. Modifica della funzione obiettivo in modo che la nuova funzione obiettivo sia ≤ cTx sul sottoinsieme Pi (ovvero ci dia un lower bound) ma renda il sottoproblema più facile. La tecnica più usata di Branching è il BRANCH BINARIO agli interi più vicini: esso consiste nel partizionare il sottoproblema Pi in due sottoproblemi Pi+1 e Pi+2 se la soluzione x ottenuta dal rilassamento lineare ha componenti non intere (frazionarie). Es: xk → vk (foto) almeno una striscia di Pi che non contiene soluzioni intere, allora avrò prima o poi soluzioni intere di rilassamenti
Per un problema di minimo descritto nel seguente modo: L è la lista dei sottoproblemi da risolvere Pi; con x^0 si indica l’ottimo corrente e con UB (upper bound) si indica il valore a questo associato. LBi è il lower bound del problema Pi e x(Si) è la soluzione ad esso corrispondente. Detto questo è possibile rappresentare lo schema del Branch e Bound per min:
Inizialmente si crea una lista L dei sottoproblemi che contiene il problema originario P 0. Poiché non si ha l’ottimo corrente gli si assegna un valore indefinito e l’UB è posto a +∞. Si scorre la lista L: se questa è vuota allora x^0 , l’ottimo corrente, è quello cercato quindi ci si ferma, se non lo è, si sceglie un sottoproblema Pi della lista L. Applicando il rilassamento al sottoproblema Pi si calcolano LBi e x(Si) e si confronta l’UB con LBi. Se UB < LBi allora si chiude il sottoproblema Pi e si torna a scorrere la lista L perché in Pi non si può trovare una soluzione migliore dell’ottimo corrente; Se UB > LBi , potrebbe esserci in Pi una soluzione migliore dell’ottimo corrente quindi si analizza l’interezza di x(Pi). Se x(Pi) è intero allora si aggiorna UB e lo si pone uguale a LBi e l’ottimo corrente diventa x^0 = x(Pi) e si torna a scorrere la lista; altrimenti si applica il braunchig a Pi introducendo in L Pi+1 e Pi+2 e si torna a scorrere la lista. Questo algoritmo è speculare per i problemi di max (dal rilassamento lineare ottengo UBi e l’ottimo corrente è un LB inizializzato a inf). Implica la risoluzione di un gran numero di rilassamenti lineari, nel caso peggiore 2n. Se si hanno invece formulazioni buone allora l’algoritmo può essere svolto più velocemente; infatti se si ha una formulazione iniziale ottima, la soluzione del rilassamento è intera e non si ha bisogno di applicare il braunch, aumentando la velocità dell’algoritmo.
Il sottoproblema Pi può essere scelto in base a 3 criteri: Quello che garantisce LB minore LIFO (last in first out) FIFO (first in first out) La scelta della variabile di Braunching può ricadere su quella più intera o su quella più frazionaria oppure secondo un ordine predefinito. Tutte le scelte influenzano l’evoluzione dell’algoritmo, e quindi i tempi di calcolo, e non c’è una scelta che risulta essere la migliore per ogni problema.
Ci sono due casi particolari di problemi di flusso intero: il problema di cammino minimo e di massimo flusso. Il problema di CAMMINO MINIMO, in cui ho dei costi cij per ogni arco ( i, j )Î A , è un problema si flusso a costo minimo in cui la rete non è capacitata e la domanda è -1 per l’origine, +1 per la destinazione e 0 per gli altri nodi. Si vuole trovare un cammino orientato da un nodo ad un altro (origine e destinazione) in modo che la somma dei costi degli archi sia minima (o massima). Il problema può essere inammissibile se tra O e D non esistono cammini orientati, illimitato inferiormente se esiste ciclo di lunghezza totale negativa (in tutti gli altri casi esiste l’ottimo). Il problema di MASSIMO FLUSSO, in cui ho un nodo sorgente s con solo archi uscenti e un nodo pozzo t di soli archi entranti, è un problema di costo minimo in cui si ha un arco da t a s di capacità infinita a costo -1, mentre gli altri hanno costo 0. Dato il nodo s sorgente e il nodo t destinazione, dati gli archi A a cui sono associate le capacità cij e dati i costi wij uguali, si vuole trovare un flusso ammissibile che massimizzi quello entrante in t (e uscente da s dato che i nodi intermedi sono solo di transito) detto flusso s-t e indicato con f(x). Se ho più sorgenti s 1 e s 2 ne creo una sola a monte, mentre se ho più possi t 1 e t 2 ne creo uno solo a valle. Ho delle capacità cij per ogni arco (i,j)ЄA ma tutti i costi sono uguali.
I dati del problema sono i seguenti: Un grafo orientato e connesso G(N,A); Un nodo sorgente s e uno destinazione t ; Esiste un cammino orientato da s ad ogni nodo uЄN; I cost i degli archi sono definiti con wuv uvЄA. Il costo di un cammino P del grafo G(N,A) è definibile nel seguente modo: Per trovare il cammino P* da s a t avente costo minimo è necessario trovare un cammino per cui valga la seguente condizione:
Possiamo rappresentare il cammino tramite il vettore di incidenza così definito: con P= cammino ottimo.
XP ha le seguenti proprietà :
la somma degli archi entranti in s deve essere uguale a 0
la somma degli archi uscenti da s deve essere 1
la somma degli archi entranti da t deve essere 1
la somma degli archi uscenti da t deve essere 0
per ogni v non appartenete a {s,t} il numero di archi entranti deve essere uguale a quello degli archi uscenti
(la domanda in s è -1 poiché da s esce il flusso, la domanda in t è +1 poiché entra il flusso e nullo in tutti gli altri archi di transi to) È possibile definire il problema del Cammino Minimo (CM):
con poliedro di cammini ammissibili da s a t.
Descritto il problema del cammino a costo minimo CM, questo può essere classificato come problema di flusso intero (G, dst, ∞|A|)
Dato un vettore x diremo che il supporto di x è l’insieme degli archi S(x)={ eЄA : xe > 0}. Il supporto è l’insieme degli archi il cui flusso è strettamente maggiore di zero. Data precedentemente la definizione iniziale di Qst, risulta che i vertici di Qst sono flussi interi ma non è vero il viceversa, ovvero che tutti i flussi interi sono vertici di Qst: infatti un vertice non può essere definito dalla combinazione lineare di punti, mentre un flusso intero si. Qst è il poliedro dei cammini da s a t definito attraverso la matrice M, la quale è totalmente uni modulare ed ha una riga ridondante così da poter riconoscere che rango(M)=(n-1). Eliminando la prima riga ottengo M’. Poiché G è convesso ho un albero ricoprente, cioè ho almeno (n-1) archi senza cicli, quindi (n-1) colonne indipendenti. Allora rango(M) ≥ (n-1) individuiamo una base B sottomatrice (n-1 x n-1) non singolare di M.
Trovare il cammino orientato P* da s a t avente costo minimo w(P*) ≤ w(P) P da s a t di G(N,A) equivale a trovare un vettore di incidenza x(P) di un cammino orientato P da s a t con
Tramite il teorema F1 si può trovare una soluzione di base, cioè un vertice x del poliedro Qst = {xЄR(A)^ : Mx=b , x≥ 0|A|} avente costo minimo wTx. Quindi per il problema di Programmaz Lineare risolvere il problema di Costo Minimo equivale a risolvere il problema di PL
Un metodo che mi permette di risolvere il problema di PL è il metodo del simplesso, ossia permette di trovare soluzioni di base (vertice) avente costo minimo.
Dato che il problema primale non ha vincoli di disuguaglianza le variabili y del vincolo non sono vincolate in segno. Perciò il duale, vista la struttura di b e M, è: Essendo il rango di M=n-1, una qualunque riga di M è ridondante e può essere eliminata. Si elimina così la variabile duale corrispondente alla riga primale, ossia y (^) s. Decidiamo di eliminare la riga del nodo s e pertanto ys=0. Pertanto il problema duale è: e se un cammino orientato da s a t, allora il problema primale ammette sempre una soluzione.
Sufficienza Sia Pu* il cammino di lunghezza minima da s a uЄ N-{s} (uЄall’insieme fa tto da tutti i nodi meno s), esiste quindi un cammino orientato tra i due nodi.
Pongo y’u = c(Pu)* uЄN{s}, ovvero si pone la variabile duale uguale al valore del costo del cammino minimo fino ad u. Se tutti i vincoli duali sono soddisfatti, cioè se y’v-y’u ≤ cuv uv ЄA (costo cammino fino a v- costo cammino fino a u ≤ costo cammino da u a v), allora y’ è una soluzione duale. Se non tutti i vincoli sono soddisfatti, cioè se y’v-y’u > cuv per qualunque valore uv ЄA, allora c(Pv)-c(Pu) > cuv** → c(Pv) > c(Pu) + cuv** Dobbiamo capire se v appartiene o meno al cammino da s a u. Ci sono 2 casi: 1- Se v non appartiene Pu* allora: P’(S,..,u,uv,v) è un cammino tale che C(P’) = c(Pu) + cuv < c(Pv)** e questa risulta essere una contraddizione; 2- Se v appartiene a Pu* allora: P’= (v,..,u) un sottocammino di Pu* da v a u risulta che C=P’ {uv} è un ciclo. Abbiamo quindi: c(Pv) > c(Pu) + C(P’) + cuv** → 0 > C(P’) + cuv = c(C) si ha quindi un ciclo negativo. Necessità (y è una soluzione duale sse G(N,A) non contiene cicli negativi) Supponiamo per assurdo che c sia un ciclo di G(N,A) con costo totale negativo (c(C)), poiché y’ è soluzione duale si ha: una contraddizione dell’ipotesi iniziale, ovvero si arriva ad una contraddizione in cui il costo del ciclo è non negativo quindi l’ipotesi iniziale è contraddetta.
Allora arrivo a dimostrare che se y’ è una soluzione duale, allora G(N,A) non ha cicli negativi.
L’algoritmo di Bellman-Ford viene implementato per trovare l’arborescenza dei cammini minimi e lo fa utilizzando le condizioni di ottimalità necessarie e sufficienti per il problema a costo minimo derivanti dalle condizioni di scarto complementare dalla teoria della dualità. SCHEMA DELL’ALGORITMO : calcolo dell’arborescenza dei cammini min dal nodo 1 al nodo i, con i=1,..,n Inizializzazione y 1 =0, yi=∞ e prec(i)=0 i=2,..,n Ordina gli archi A={e 1 ,..,em} Repeat (fin quano y non si modifica più) For k=1 to m (per ogni arco) if ek=(i,j) è tale che yj > yi + cij
Pijd^ =(i,k 1 ,k 2 ,..,kq,j) con kn Є Nd={1,2,..,d} il cammino minimo tra i e j con nodi interni solo ad Nd; dijk^ il costo associato al cammino minimo Pijd; Dk=[ dijk] con i,j=1,..,n la matrice dei costi del cammino Pijd; D^0 =[Wij] i,j=1,..,n la matrice dei costi associati agli archi del grafo G; Dn^ la matrice dei costi dei cammini minimi tra i e j con nodi interni nell’insieme N. Lo schema dell’algoritmo è il seguente: Inizializzazione : for i:=1 to n for k:=1 to n for j:= 1 to n for i:=1 to n do Begin for j:=1 to n D[i,j] := w(i,j); do Begin pred [i,j] := i; if D[i,j] >D[i,k] + D[k,j] end; then Begin D[i,j] = D[i,k] + D[k,j]; pred[i,j] = pred[k,j]; end; pred[i,j]= predecessore fi j nel cammino da i a j; se D[i,i]<0 c’è un ciclo negativo che passa per il nodo i;
L’algoritmo permette di determinare un collegamento diretto dalla matrice D 0 alla matrice Dn, cioè quella finale che si ottiene ispezionando tutti i nodi. D^0 → D^1 … Dk-1^ → Dk^ … Dk^ → Dn L’inizializzazione prevede di determinare la matrice D^0 ponendo ogni componente ij uguale al costo del cammino che va da i a j (D[i,j] := W[i,j]), analogamente costruisco la matrice dei predecessori ponendo il predecessore di j nel cammino tra i e j uguale a i (pred[i,j] := i). Per quanto riguarda le strutture dati, ovvero il corpo centrale dell’algoritmo, si itera k volte con k definito come il numero dei nodi interno di Nd. Per ciascuna iterazione k-esima è necessario verificare a seguente condizione: D[i,j] > D[i,k] + D[k,j] Se questa risulta verificata allora si pone D[i,j] :=D[i,k] +D[k,j] , pred[i,j] := pred[k,j]. Per passare dalla matrice Dk-1=[dijk] i,j=1,..,n che rappresenta la matrice dei costi dei cammini minimi che hanno nodi Nk-1 ={1,2,..,k-1} alla matrice Dk=[dijk] i,j=1,..,n , ovvero la matrice dei costi dei cammini minimi Pijk^ che hanno i nodi Nk={1,2,..,k}. Si devono distinguere due possibili casi scegliendo quello più conveniente tra: -Pijk^ non utilizza il nodo k; -Pijk^ utilizza il nodo k. La formula di aggiornamento della matrice D è: dijk^ = min {dij(k-1)^ , dik(k-1)^ + dkj(k-1)} che determina il costo minimo del cammino Pijk^ tra quello passante e quello non per k
Il problema di massimo flusso (MF) si propone di massimizzare il flusso uscente dl nodo s ed entrante nel nodo t.