Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea...

45
Lez. 10a 1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per la progettazione di algoritmi: divide & conquer problema del min-max quicksort Copyright © 2007-2008 by Claudio Salati.

Transcript of Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea...

Page 1: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

Lez. 10a 1

Universita' di FerraraFacolta' di Scienze Matematiche, Fisiche e Naturali

Laurea Specialistica in Informatica

Algoritmi Avanzati

Strategie per la progettazione di algoritmi:divide & conquer

• problema del min-max• quicksort

Copyright © 2007-2008 by Claudio Salati.

Page 2: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

2

DIVIDE-&-CONQUER

• Nella progettazione di un algoritmo la strategia e' quasi sempre quella di suddividere il problema in sottoproblemi piu' semplici.  

• Dato un problema P su un insieme di dati di dimensione n una maniera di suddividerlo in problemi piu' semplici e' quella di

considerare problemi analoghi a P ma su insiemi di dati di dimensione minore(cioe' problemi piu' piccoli: piccolo e' facile)

• SI RICONDUCE LA SOLUZIONE DI P, dove #P = n, ALLA SOLUZIONE DI m PROBLEMI P1, P2, …, Pm,

dove i | 1i m : # Pi = n/k

• OVVIAMENTE BISOGNA CHE SIA FACILE:

• OPERARE LA SCOMPOSIZIONE

• RICOMPORRE LE m SOLUZIONI PARZIALI NELLA SOLUZIONE COMPLESSIVA

Page 3: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

3

DIVIDE-&-CONQUER

• PERCHE' CONSIDERARE LO STESSO PROBLEMA SOLO PER DIMENSIONI PIU' PICCOLE DOVREBBE ESSERE CONVENIENTE?

• PERCHE' SE IL PROBLEMA E' DI COMPLESSITA' n2 DIVIDERLO PER 2 SIGNIFICA OTTENERE UN PROBLEMA 4 VOLTE PIU' FACILE!

• Non solo, OPERANDO RICORSIVAMENTE SI ARRIVA AD OTTENERE PROBLEMI ELEMENTARI:

e.g., ORDINARE UN VETTORE DI LUNGHEZZA 1 E' MOLTO FACILE, E' GIA' DI PER SE STESSO ORDINATO

Page 4: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

4

DIVIDE-&-CONQUER

void divideAndConquer(items data [],  int fromItem, int toItem)

{

// risolve il problema per il sottovettore // data[fromItem..toItem];// la risoluzione si suppone sul posto

if (smallEnough(fromItem, toItem))

solve(data, fromItem, toItem);

else {  int middle = (fromItem + toItem) / 2; // splitProblem(data, fromItem, toItem, // &middle);  divideAndConquer(data, fromItem, middle); divideAndConquer(data, middle + 1, toItem);  combine(data, fromItem, toItem, middle);

}

}

Page 5: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

5

DIVIDE-&-CONQUER

• IL PARTIZIONAMENTO AVVIENE DI NORMA VERSO PROBLEMI BILANCIATI, DI UGUALE DIMENSIONE

• SBILANCIARE NON CONVIENE

• SUPPONIAMO DI APPLICARE MERGESORT A 2 SOTTOPROBLEMI SBILANCIATI:

• T(n) = T(1) + T(n-1) + T(merge, 1, n-1)

• T(1) E' COSTANTE

• T(merge, 1, n-1) E' O(n)

• E LA COMPLESSITA' TOTALE E' O(n2)

• INFATTI CON LO SBILANCIAMENTO SI E' TRASFORMATO MERGESORT IN STRAIGHT-INSERTION!

Page 6: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

6

DIVIDE-&-CONQUER

• SE g(n) E' LA COMPLESSITA' DELLA SOLUZIONE DI UN

PROBLEMA smallEnough()

• E f(n) E' LA COMPLESSITA' DI combine() 2 SOLUZIONI PARZIALI, CIASCUNA DI DIMENSIONE n/2

• ALLORA LA COMPLESSITA' DI divideAndConquer() E'

• T(n) = g(n) per n

smallEnough()

• T(n) = 2 * T(n/2) + f(n) per n !smallEnough() 

• La complessita’ della operazione di scomposizione del problema in due sotto-problemi (che nello schema di funzione

coincide con il calcolo di middle) e’ supposta assorbibile

entro la complessita' di combine()

Page 7: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

7

DIVIDE-&-CONQUER

• Vogliamo valutare il costo T(n) di risolvere un problema di dimensione n

• SUPPONIAMO DI DIVIDERE UN PROBLEMA DI DIMENSIONE n IN a SOTTOPROBLEMI DI DIMENSIONE n/b CIASCUNO

• E CHE IL LAVORO PER OPERARE LA RICOMBINAZIONE DELLE SOLUZIONI PARZIALI SIA c * nd

(INGLOBANDO IN QUESTO ANCHE L'EVENTUALE COSTO DEL PARTIZIONAMENTO IN SOTTOPROBLEMI)

• E SUPPONIAMO CHE RISOLVERE UN PROBLEMA DI DIMENSIONE 1 ABBIA COSTO COSTANTE k1

• ALLORA a * T(n/b) E' IL COSTO DI RISOLVERE TUTTI I SOTTOPROBLEMI

Page 8: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

8

DIVIDE-&-CONQUER

• Definizione ricorsiva di T(n):

T(n) = c * nd + a * T(n/b)

T(1) = k1

• espandiamo ricorsivamente T(n/b)

T(n) = c * nd + a * (c * (n/b)d + a * T(n/b2))

= c * nd * (1 + a/bd) + a2 * T(n/b2)

• e continuando ad espandere ricorsivamente per p=logbn volte

T(n) = c * nd * (1 + a/bd + … + (a/bd)p-1) + ap * T(1)

• ma ap = a = (b ) = (b ) = nlogbn logba logbn logbn logba logba

{

j1p

0jd

dalog1

b

a*n*cn*k)n(T b

Page 9: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

9

DIVIDE-&-CONQUER

cioe' (se x1)

e

1nn

0j

j1n

0j

jn

0j

j x*ax*a*xax*a*xax*a

)x1(*ax*a*)x1( 1nn

0j

j

x1

x1*ax*a

1nn

0j

j

Page 10: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

10

DIVIDE-&-CONQUER

• se x<1 allora

per cui k2 maggiora la sommatoria per qualsiasi n finito

• se x=1 allora la sommatoria vale (n+1)*a

• se x>1 per n sufficientemente grande la sommatoria e' maggiorata da a*xn+1

2

1n

nk

x1

a

x1

x1*alim

Page 11: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

11

DIVIDE-&-CONQUER

• N.B.: la sommatoria e' quella dei primi n termini della serie geometrica

• La serie geometrica e la sua sommatoria

• convergono per x < 1

• divergono per x > 1

• Per x = 1 la sommatoria della serie geometrica diverge

• Per x>1 e n abbastanza grande la sommatoria della serie geometrica coincide approssimativamente, a meno di costanti moltiplicative, con il suo ultimo termine (o meglio, con il termine successivo, per tenere conto dei termini precedenti)

• N.B.: nel nostro caso x = a / bd

Page 12: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

12

DIVIDE-&-CONQUER

a < bd

• Caso: x = a / bd < 1

e quindi, poiche' logba < d :

• in questo caso domina il lavoro non ricorsivo di ricomposizione dei risultati parziali

d2

alog1 n*c*kn*k)n(T b

)n(O)n(O)n(T dalogb

)n(O)n(T d

Page 13: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

13

DIVIDE-&-CONQUER

a > bd

• Caso: x = a / bd > 1

• ma:

• e quindi:

• in questo caso domina il lavoro ricorsivo

p

ddalog

1b

a*n*cn*k)n(T b

dalogb

alognlog

nlog

b

alognlog

d

p

dbdb

b

b

dbb

nbbb

a

b

a

)n(O)n(T alogb

Page 14: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

14

DIVIDE-&-CONQUER

a = bd

• Caso: x = a / bd = 1

• e quindi:

• in quanto logba=d

• in questo caso il lavoro ricorsivo e quello di ricomposizione si bilanciano, e compare il termine logaritmico

nlog*n*cn*k)n(T bdalog

1b

)nlog*n(O)n(T bd

Page 15: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

15

DIVIDE-&-CONQUER

Riassumendo:

• se a bd

• se a = bd )nlog*n(O)n(T bd

)n(O)n(T )alog,dmax( b

Page 16: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

16

DIVIDE-&-CONQUER

Nel caso del mergesort:

• a = 2

• b = 2

• d = 1

– quindi: a = bd

– quindi: T(n) = O(n * log2n)

Nel caso dell’algoritmo del torneo:

• a = 2

• b = 2

• d = 0

– quindi: a > bd

– quindi: T(n) = = O(n))O(n alogb

Page 17: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

17

DIVIDE-&-CONQUER

In generale, se

allora

salvo che le due quantita' maggiori siano uguali. In questo caso e':

d

kk

22

11 n*c

b

nT*a...

b

nT*a

b

nT*a)n(T

)n(O)n(T)alog,...,alog,alog,dmax( kkb22b11b

))nlog(*n(O)n(T)alog,...,alog,alog,dmax( kkb22b11b

Page 18: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

18

DIVIDE-&-CONQUER: esempio

• Immaginiamo di dovere individuare elemento minimo e massimo di un vettore.

• L'algoritmo seguente fornisce una soluzione banale del problema

typedef . . . elemento;struct result { elemento min; elemento max; };struct result easyMinMax(elemento v[], int n) { 1

assert(n>0); struct result res; 2

res.min = res.max = v[0]; 3

for (int i=1; i<n; i+=1) { 4

if (v[i] < res.min) res.min = v[i]; 5

if (v[i] > res.max) res.max = v[i]; 6

} 7

return (res); 8

}

Page 19: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

19

DIVIDE-&-CONQUER: esempio

• Per analizzare la complessita' dell'algoritmo ci si concentra sul numero di confronti tra elementi del vettore che esso esegue.

• perche' le altre operazioni sono in numero proporzionale a questi confronti.

• perche' se gli elementi sono oggetti complessi (e.g. stringhe) il costo di questi confronti e' predominante rispetto al costo delle altre operazioni.

• la complessita' di easyMinMax() e' evidentemente 2*(n-1).

• 2*(n-1) rappresenta caso migliore, peggiore, e medio.

• e' anche immediato vedere come easyMinMax() puo' essere migliorata:

se v[i]<res.min non puo' essere v[i]>res.max

quindi il secondo if (riga 6) deve essere eseguito solo se la condizione del primo (riga 5) risulta falsa

Page 20: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

20

DIVIDE-&-CONQUER: esempio

typedef . . . elemento;

struct result { elemento min;

elemento max; };struct result betterMinMax(elemento v[], int n) { 1

assert(n>0); struct result res; 2

res.min = res.max = v[0]; 3

for (int i=1; i<n; i+=1) { 4

if (v[i] < res.min) res.min = v[i]; 5

else if (v[i] > res.max) res.max = v[i]; 6

// end if } 7

return (res); 8

} 9

Page 21: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

21

DIVIDE-&-CONQUER: esempio

• la complessita' di betterMinMax() non e' piu' sempre la stessa per i casi migliore, peggiore, e medio.

• il caso migliore si ha quando v[] e' ordinato in modo non crescente: in questo caso il numero di confronti e' n-1.

• il caso peggiore si ha quando v[] e' ordinato in modo non decrescente: in questo caso il numero di confronti e' 2*(n-1).

• nel caso medio sara' v[i]<res.min meta' delle volte e quindi il numero medio di confronti sara' 3*(n-1)/2.

• e' possibile fare "di meglio"?

• applichiamo la strategia divide & conquer!

Page 22: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

22

DIVIDE-&-CONQUER: esempio

typedef . . . elemento;typedef struct result { elemento min; elemento max; } result;result dAndCMinMax(elemento v[], 1

int from, int to) { assert(0<=from && from<= to && to<=#v); result res; 2

if (to-from <= 1) { 3

// 1 o 2 elementi nel sottovettore if (v[from] <=v [to]) { 4

res.min = v[from]; res.max = v[to]; 5

} else { 6

res.min = v[to]; res.max = v[from]; 7

} 8

} else { 9

// continua alla pagina seguente

Page 23: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

23

DIVIDE-&-CONQUER: esempio

// continuazione di dAndCMinMax()

// piu' di 2 elementi nel sottovettore int mid = (from + to) / 2; 10

result r1 = dAndCMinMax(v, from, mid); 11

result r2 = dAndCMinMax(v, mid+1, to); 12

res.min = (r1.min <= r2.min) ? r1.min 13

: r2.min; 14

res.max = (r1.max >= r2.max) ? r1.max 15

: r2.max; 16

} 17

return (res); 18

} 19

Page 24: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

24

DIVIDE-&-CONQUER: esempio

• dAndCMinMAX() correttezza:

• per esercizio (elementare per induzione matematica).

• dAndCMinMAX() complessita':

• e' data dalla seguente relazione ricorsiva:

• T(1) = T(2) = 1

• T(n : n>2) = 2 * T(n/2) + 2

• T(n) = 2 * (2 * T(n/4) + 2) + 2 = 4 * T(n/4) + (4+2)

= 4 * (2 * T(n/8) + 2) + (4+2) = 8 * T(n/8) + (8+4+2)

= ...

• e per k tale che 2k=n 22

n*3)22(22)2(T*2)n(T k1k

1k

1i

i1k

Page 25: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

25

DIVIDE-&-CONQUER: esempio

• N.B.: la complessita' calcolata per dAndCMinMAX() si applica in tutti i casi, peggiore, migliore e medio.

• In effetti e' dimostrabile che nessun algoritmo basato su confronti puo' richiedere meno di 3*n/2-2 confronti.

• Ma dAndCMinMAX() e' davvero migliore di betterMinMax()?

• in termini di complessita' spaziale e' peggiore: richiede l'allocazione di log(n) record di attivazione ricorsiva.

• nel confronto si potrebbero contare anche le altre operazioni, e allora il vantaggio di dAndCMinMAX() diventerebbe minore.

• c'e' poi da considerare l'overhead temporale delle chiamate ricorsive.

• Cio' dimostra l'importanza, in certe circostanze, di considerare i coefficienti moltiplicativi e i termini di grado inferiore nelle funzioni che descrivono la complessita' degli algoritmi.

Page 26: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

26

ALGORITMI DI ORDINAMENTO PER CONFRONTO

Algoritmo O(n2) Corrispondente algoritmo O(n*log(n))

straight insertion mergesort

straight selection heapsort

bubblesort ?

• Straight insertion si basa sulla creazione di un sottovettore localmente ordinato e sull'inserimento in esso, uno dopo l'altro, degli elementi restanti del vettore

• Mergesort si basa sulla creazione di due sottovettori localmente ordinati e sulla loro fusione ordinata

• Straight selection, heapsort e bubblesort si basano sulla creazione di un sottovettore globalmente ordinato e con la sua estensione successiva con gli elementi del restante sottovettore disordinato

• N.B.: tra sottovettore ordinato e sottovettore disordinato esiste una precisa relazione: tutti gli elementi del primo sono di tutti gli elementi del secondo

Page 27: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

27

ALGORITMI DI ORDINAMENTO PER CONFRONTO

• Straight insertion si basa

– sulla creazione di 2 sottovettori, un sottovettore localmente ordinato e un sottovettore non ordinato (senza alcuna relazione d’ordine tra gli elementi di un sottovettore e quelli dell’altro)

– sull'inserimento nel sottovettore ordinato, uno dopo l’altro, degli elementi del sottovettore non ordinato

• Mergesort si basa

– sulla creazione di 2 sottovettori, entrambi localmente ordinati (senza alcuna relazione d’rdine tra gli elementi di un sottovettore e quelli dell’altro)

– sul merge ordinato dei 2 sottovettori

– sull’uso della strategia Divide&Conquer

Page 28: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

28

ALGORITMI DI ORDINAMENTO PER CONFRONTO

• Straight selection si basa

– sulla creazione di 2 sottovettori, un sottovettore globalmente ordinato e un sottovettore non ordinato (gli elementi del sottovettore non ordinato sono tutti maggiori o uguali degli elementi del sottovettore globalmente ordinato)

– sull'inserimento nel sottovettore ordinato dell’elemento minimo del sottovettore non ordinato

• Heapsort si basa

– sulla creazione di 2 sottovettori, un sottovettore globalmente ordinato e un sottovettore non ordinato (gli elementi del sottovettore non ordinato sono tutti minori o uguali degli elementi del sottovettore globalmente ordinato)

– sul fatto che il sottovettore non ordinato e’ costituito da uno heap basato sulla relazione “maggiore o uguale”

– sull'inserimento nel sottovettore ordinato dell’elemento massimo del sottovettore non ordinato

– sull’uso della differenziazione formale

Page 29: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

29

ALGORITMI DI ORDINAMENTO PER CONFRONTO

• Straight exchange e/o bubblesort si basano

– sulla creazione di 2 sottovettori, un sottovettore globalmente ordinato e un sottovettore non ordinato (gli elementi del sottovettore non ordinato sono tutti maggiori o uguali degli elementi del sottovettore globalmente ordinato)

– sull’utilizzo di una successione di scambi con elementi adiacenti del sottovettore non ordinato per portare un elemento del sottovettore non ordinato al proprio posto nel sottovettore ordinato

• Quicksort si basa

– sull’applicazione della strategia Divide&Conquer

– sull’utilizzo, per spostare un elemento verso la sua posizione corretta, di salti il piu’ lunghi possibile

Page 30: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

30

QUICKSORT

• Come saranno i due sottovettori in cui viene suddiviso il vettore da ordinare secondo la strategia Divide&Conquer?

• Non possono essere entrambi globalmente ordinati, altrimenti le 2 chiamate ricorsive e la funzione combine() non avrebbero niente da fare, avrebbe fatto gia’ tutto la funzione splitProblem()!

• Quindi almeno inizialmente non potranno essere ordinati, saranno le chiamate ricorsive a ordinarli.

• Ma la relazione d’ordine tra i due sottovettori?

• Ma la relazione d’ordine tra i due sottovettori?

• La si conserva!

• La funzione splitProblem() dovra’ essere tale da suddividere il vettore in 2 sottovettori tali che gli elementi dell’uno sono tutti minori o uguali degli elementi dell’altro.

• La funzione combine() sara’ vuota!

Page 31: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

31

QUICKSORT

• Quicksort si basa come bubblesort sullo scambio di elementi disordinati.

• Lo scambio di elementi in quicksort non ha lo scopo di mettere in ordine elementi adiacenti.

• Lo scambio in quicksort non avviene tra elementi adiacenti.

• Gli elementi fanno degli spostamenti maggiori: e' per questo che ci si aspetta un comportamento migliore di quello di bubblesort

• Lo scambio di elementi in quicksort ha lo scopo di creare due sottovettori che abbiano la seguente proprieta':

Proprieta' P: Tutti gli elementi del primo sottovettore sono minori o uguali di tutti gli elementi del secondo sottovettore.

• Per ottenere un vettore ordinato e’ quindi sufficiente ordinare localmente ciascuno dei due sottovettori ottenuti dal partizionamento del vettore.

• L'ordinamento dei due sottovettori e' ovviamente possibile applicando ricorsivamente la procedura.

Page 32: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

32

QUICKSORT

i = 0..m-1: v[i] v[m]

i = m+1..N-1: v[i] v[m]

• e quindi:

i = 0..m-1, j = m+1..N-1 : v[i] v[j]

• L'operazione di suddivione del vettore nei due sottovettori separati dall'elemento pivot m e' chiamata partizionamento

v[0] v[1] v[N-1]...vettore v

v[0] ... v[m] v[N-1]...vettore v

Page 33: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

33

QUICKSORT: l’elemento pivot

• L’elemento pivot dovrebbe essere l’elemento mediano del vettore v

• In questo modo i due sottovettori alla sua destra e alla sua sinistra sarebbero bilanciati

• Ma come e’ possibile conoscere a priori quale e’ l’elemento mediano del vettore?

• Ci vorrebbe un oracolo.

• In mancanza dell’oracolo ci si affida al calcolo delle probabilita’: si utilizza come pivot un elemento a caso, il piu’ comodo, il primo elemento del (sotto-)vettore.

Page 34: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

34

QUICKSORT: l'algoritmo

void quicksort(int v[], int from, int to) {

if (to > from) {

int m = partition(v, from, to);

quicksort(v, from, m-1);

quicksort(v, m+1, to);

}

}

• La funzione partition() effettua il partizionamento del vettore v[] in due sottovettori che soddisfano la proprieta' P intorno all'elemento pivot di indice m

• Per ordinare il vettore int v[n] e' sufficiente chiamare

quicksort(v, 0, n-1);

Page 35: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

35

QUICKSORT: funzione partition() .1

int partition(int v[], int from, int to) { assert(to>from); int pivot = v[from]; // seleziono il pivot int fromScan = from+1; int toScan = to; // i=from+1..fromScan-1: v[i]v[from] // i=toScan+1..to: v[i]v[from] for (;;) { while (fromScan <= toScan && v[fromScan] <= pivot) fromScan += 1; while (toScan >= fromScan && v[toScan] >= pivot) toScan -= 1;

// continua alla pagina successiva

Page 36: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

36

QUICKSORT: funzione partition() .2

// int partition(): continua if (toScan > fromScan) { int temp = v[fromScan]; v[fromScan] = v [toScan]; v[toScan] = temp; fromScan += 1; toScan -= 1; } else { break; } } assert (toscan == fromscan-1); int m = fromScan - 1; v[from] = v[m]; v[m] = pivot; return(m);}

Page 37: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

37

QUICKSORT: correttezza .1

Teorema: La funzione partition() suddivide il sottovettore v[from..to] in tre parti (la prima o la terza eventualmente vuote):

• il sottovettore v[from..m-1]

• l'elemento v[m]

• il sottovettore v[m+1..to]

tali che:

k = from .. m-1: v[k] v[m]

k = m+1 .. to: v[m] v[k]

Dimostrazione:

• Discende immediatamente dall'invariante del ciclo esterno e dal fatto che tale ciclo termina quando toScan=fromScan-1.

• L'elemento v[m] al termine della funzione e' uguale all'elemento v[from] all'inizio di essa.

Page 38: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

38

QUICKSORT: correttezza .2

Teorema: La funzione quicksort() ordina il sottovettore v[from..to] in modo non decrescente.

Dimostrazione:

• Per induzione matematica sulla lunghezza del sottovettore v[from..to].

• Ciascuno dei due sottovettori delle chiamate ricorsive e' lungo al piu' to-from, per cui l'ipotesi induttiva e' applicabile.

• Dopo le chiamate ricosive i due sottovettori sono ordinati: la correttezza globale discende dalla correttezza della funzione partition().

Page 39: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

39

QUICKSORT: complessita' .1

• L'algoritmo quicksort ha complessita' O(n2).

• Nel caso peggiore infatti ogni partizionamento avviene con uno dei due sottovettori vuoto.

• La chiamata ricorsiva e' quindi per un sottovettore di lunghezza inferiore di un solo elemento a quella del sottovettore della attivazione chiamante.

• Si hanno quindi n attivazioni della funzione e ogni attivazione, relativa ad un sottovettore di lunghezza k, effettua k-1 confronti.

• Nel caso migliore pero' il partizionamento e’ con sottovettori bilanciati: in questo caso l'altezza dell'albero delle chiamate ricorsive e' solo log(n) e il comportamento dell'algoritmo diventa di complessita' n*log(n).

• La domanda quindi e':

• Quale e' il comportamento atteso?

• Quale e' il comportamento medio?

Page 40: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

40

QUICKSORT: complessita' media .2

• L'ipotesi e' che tutte le permutazioni della sequenza di elementi da ordinare siano equiprobabili.

• Sia T(n) la complessita' dell'algoritmo nell'ordinamento di un sottovettore di lunghezza n:

• T(0) = T(1) = b (costante)

• T(n) = (n - 1) + T(i-1) + T(n-i), per n 2, con i = 1..n

essendo i la posizione nel sottovettore partizionato dell'elemento pivot.

• Nell'ipotesi fatta i puo' assumere qualunque valore tra 1 e n con uguale probabilita', per cui in media

(1)

1n

0i

n

1i

)i(T*n

2)1n(

))in(T)1i(T(*n

1)1n()n(T

Page 41: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

41

• Proviamo se la relazione e' soddisfatta da T(n) = c * n * log(n) (che e' la complessita' "desiderata").

• Sostituiamo nella relazione ricorsiva (1):

(2)

• Quanto vale la sommatoria che compare in (2)?

QUICKSORT: complessita' media .3

?

1n

1j

)jlog(*j*n

c*21n)nlog(*n*c

Page 42: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

42

• Consideriamo una generica funzione monotona crescente f(x)

(3)

QUICKSORT: complessita' media .4

n

k

nn

k

)k(fdx)x(f)k(f1

1

11

1

Page 43: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

43

Ma

per cui, sottraendo (f(n) - f(1)) dall'integrale di (3):

(4)

consideriamo allora f(x) = x * ln(x)

tenendo conto che

e sostituendo nella disequazione (4)

(vedi pagina seguente)

QUICKSORT: complessita' media .5

)f()nf()k(f)k(fn

k

n

k

11111

1

11

1

1

11nn

k

n

dx)x(f)k(f))(f)n(f(dx)x(f

42

22 x)xln(

xdx)xln(x

Page 44: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

44

cioe'

QUICKSORT: complessita' media .6

4

10

4

n)nln(*

2

n

)kln(k

)0)nln(n(4

10

4

n)nln(*

2

n

22

1n

1k

22

4

1

4

n)nln(

2

n)kln(k

221n

1k

Page 45: Lez. 10a1 Universita' di Ferrara Facolta' di Scienze Matematiche, Fisiche e Naturali Laurea Specialistica in Informatica Algoritmi Avanzati Strategie per.

45

E dividendo per ln(2)

che sostituiamo nella relazione ricorsiva (2):

quindi, a meno di termini di ordine minore: T(n) = O(n*log(n))

QUICKSORT: complessita' media .7

)2ln(*4

1

)2ln(*4

n)nlog(

2

n)klog(k

221n

1k

n*)2ln(*2

c1n*

)2ln(*2

c1)nlog(*n*c

)2ln(*4

1

)2ln(*4

n)nlog(

2

n

n

c21n

22