Upload
stefano-fanelli
View
214
Download
1
Embed Size (px)
DESCRIPTION
Algoritmi
Citation preview
D O T T. I N G . L E O N A R D O R I G U T I N I D I PA R T I M E N T O I N G E G N E R I A D E L L I N F O R M A Z I O N E
U N I V E R S I T D I S I E N A V I A R O M A 5 6 5 3 1 0 0 S I E N A
U F F. 0 5 7 7 2 3 4 8 5 0 - 7 1 0 2 R I G U T I N I @ D I I . U N I S I . I T
H T T P : / / W W W. D I I . U N I S I . I T / ~ R I G U T I N I /
Algoritmi di Ordinamento
Algoritmo di ordinamento
Metodo per ordinare un insieme di oggetti.
Il problema dellordinamento un problema classico dellinformatica: - Valenza didattica: problema in s molto semplice e chiunque in
grado di comprendenre i termini generali - Valenza in ambito applicativo: si ritrova spesso come sottoproblema
in molti casi reali
Sono stati proposti molti algoritmi diversi ed eleganti: - Se presentati in opportuna successione permettono di evidenziare gli
aspetti fondamentali della progettazione e della costruzione di un algoritmo efficiente
Algoritmo di ordinamento
Il problema dellordinamento (sorting) pu essere posto nei seguenti termini: - Dati un insieme di elementi qualsiasi A={a1,a2,,an}, su cui sia
possibile definire una relazione dordine totale si richiede diprodurre una permutazione degli elementi in modo che aih aik per ogni h,k=1,2,.,n e h k
- Una relazione dordine totale una relazione riflessiva, antisimmetrica e transitiva definita su ogni coppia di elementi dellinsieme
- La soluzione unica a meno di elementi uguali:
Algoritmi di ordinamento
Soluzioni via via sempre pi sofisticati ma con complessit computazionale sempre pi bassa
Algoritmi di ordinamento
I primi 3 algoritmi analizzat SELECTION SORT, INSERTION SORT e BUBBLE SORT sono estremamente elementari e consentono unimplementazione assai semplice: - il costo da pagare alla semplicit di questi algoritmi sta ovviamente
nellelevata complessit computazionale,che inquesti casi O(n2).
Lalgoritmo QUICKSORT consente di raggiungere una complessit di O(nlog2n) nel caso medio, mentre nel caso pi sfavorevole ritorna ad una complessit di O(n2).
Algoritmi di ordinamento
Gli algoritmi MERGESORT e HEAPSORT consentono di raggiungere una complessit di O(nlog2n) anche nel caso peggiore: - possibile dimostrare che il limite inferiore alla complessit
computazionale del problema dellordinamento mediante confronti (senza dunque poter sfruttare altre informazioni sullinsieme da ordinare) proprio pari a nlog2n, possiamo concludere che tali algoritmi sono ottimi.
Algoritmi di ordinamento
Gli algoritmi COUNTING SORT e BUCKET SORT sono invece basati su altri criteri e strategie, diverse dal confronto fra i valori degli elementi dellinsieme da ordinare, e sfruttano pertanto altre informazioni sui dati in input: - Grazie a questo consentono di ridurre ulteriormente la complessit
nel caso peggiore, arrivando ad una complessit lineare di (n). Sotto a tale soglia impossibile scendere,dal momento che per ordinare un insieme di n elementi necessario esaminarli tutti almeno una volta.
Ci possiamo concentrare soltanto nello studio della complessit nel caso peggiore, dal momento che il parametro pi conservativo per la valutazione dellefficienza di un algoritmo.
Selection sort
Selection sort
Un algoritmo decisamente intuitivo ed estremamente semplice.
Nella pratica utile quando linsieme da ordinare composto da pochi elementi e dunque anche un algoritmo non molto efficiente pu essere utilizzato con il vantaggio di non rendere troppo sofisticata la codifica del programma che lo implementa.
Lidea di fondo su cui si basa lalgoritmo quella di ripetere per n volte una procedura in grado di selezionare alla i-esima iterazione lelemento pi piccolo nellinsieme e di scambiarlo con lelemento che in quel momento occupa la posizione i
Selection sort
In altre parole: - alla prima iterazione dellalgoritmo verr selezionato lelemento pi
piccolo dellintero insieme e sar scambiato con quello che occupa la prima posizione;
- alla seconda iterazione selezionato il secondo elemento pi piccolo dellinsieme, ossia lelemento pi piccolo dellinsieme ridottocostituito dagli elementi {a2,a3,...,an}ed scambiato con lelemento che occupa la seconda posizione;
- Si ripete fino ad aver collocato nella posizione corretta tutti gli n elementi.
Selection Sort
void selection_sort(int[] A, int n) { int i=0; for (i=0;i
Selection Sort
Il numero di operazioni : (n-1) + (n-2) + + 2 + 1 n(n-1)/2 O(n2)
Un inconveniente dell'algoritmo di ordinamento per selezione che il tempo di esecuzione dipende solo in modo modesto dal grado di ordinamento in cui si trova il file. La ricerca del minimo elemento durante una scansione del file non fornisce informazioni circa la posizione del prossimo minimo nella scansione successiva.
Verificare che esso impiega pi o meno lo stesso tempo sia su file gi ordinati che su file con tutte le chiavi uguali, o anche su file ordinati in modo casuale.
Selection Sort
Nonostante l'approccio brutale adottato, ordinamento per selezione ha un'importante applicazione: poich ciascun elemento viene spostato al pi una volta, questo tipo di ordinamento il metodo da preferire quando si devono ordinare file costituiti da record estremamente grandi e da chiavi molto piccole. Per queste applicazioni il costo dello spostamento dei dati prevalente sul costo dei confronti e nessun algoritmo in grado di ordinare un file con spostamenti di dati sostanzialmente inferiori a quelli dell'ordinamento per selezione.
Insertion sort
Insertion Sort
Ordinamento a inserimento, un algoritmo relativamente semplice per ordinare un array.
Non molto diverso dal modo in cui un essere umano, spesso, ordina un mazzo di carte.
Algoritmo in place, cio ordina l'array senza doverne creare una copia, risparmiando memoria.
Insertion Sort
Ad ogni istante (iterazione), il vettore costituito da una parte iniziale ordinata (che aumenta di volta in volta) e da la parte rimanente che contiene i valori da ordinare.
Per ogni valore ancora da inserire, viene fatta una ricerca binaria nella parte ordinata del vettore e vengono spostati in avanti tutti gli elementi per liberare la posizione
Nella posizione liberata viene inserito il valore
Insertion Sort
Complessit: - Caso peggiore O(n2) - Caso migliore O(n) vettore gi ordinato
Molto vantaggioso per vettori quasi ordinati
Bubble sort
Bubble Sort
Lalgoritmo BUBBLE SORT (ordinamento a bolle) so basa sullidea di far emergere pian piano gli elementi pi piccoli verso linizio dellinsieme da ordinare facendo sprofondare gli elementi maggiori verso il fondo: - un po come le bollicine in un bicchiere di acqua gassata da qui il
nome di ordinamento a bolle.
La strategia adottata quella di scorrere pi volte la sequenza da ordinare, verificando ad ogni passo lordinamento reciproco degli elementi contigui, ai e ai+1, ed eventualmente scambiando la posizione di quelle coppie di elementi non ordinate.
Bubble Sort
Procedendo dallinizio alla fine della sequenza, al termine di ogni scansione si ottenuto che lelemento massimo finito in fondo alla sequenza stessa, mentre gli elementi pi piccoli hanno cominciato a spostarsi verso linizio della sequenza stessa.
Dunque alla fine della prima scansione possiamo essere certi che lelemento massimo ha raggiunto la sua posizione corretta nellultima posizione della sequenza: - la scansione successiva potr fermarsi senza considerare lultimo
elemento dellinsieme e riuscendo cos a collocare nella posizione corretta (la penultima) il secondo elemento pi grande dellinsieme;
Si ripete fino ad aver completato lordinamento dellintera sequenza.
Bubble Sort void bubble_sort(int[] A, int n) { bool scambio=true; int ultimo=n-1,i=0; while (scambio) { scambio=false; for (i=0;ia[i+1]) { int temp=a[i]; a[i]=a[i+1]; a[i+1]=temp; scambio=true; } } ultimo--; } }
Bubble Sort
Il numero di operazioni : (n-1) + (n-2) + + 2 + 1 n(n-1)/2 O(n2)
Quick Sort
Quick Sort
Quicksort un algoritmo di ordinamento ricorsivo in place che si basa sul paradigma divide et impera.
La base del suo funzionamento l'utilizzo ricorsivo della procedura partition: - preso un elemento da un array si pongono gli elementi minori a
sinistra rispetto a questo e gli elementi maggiori a destra - La stessa procedura poi richiamata in modo ricorsivo sui due sotto
insiemi
Il Quicksort, termine che tradotto letteralmente in italiano indica ordinamento rapido, l'algoritmo di ordinamento che ha, in generale, prestazioni migliori tra quelli basati su confronto.
Approccio ricorsivo
L'idea base pu esprimersi agevolmente in termini ricorsivi. - Ad ogni stadio si effettua un ordinamento parziale di una sequenza di
oggetti da ordinare. Assunto un elemento come perno dello stadio, si confrontano con esso gli altri elementi e si posizionano alla sua sinistra i minori e a destra i maggiori, senza tener conto del loro ordine. Dopo questo stadio si ha che il perno nella sua posizione definitiva.
- Successivamente si procede in modo ricorsivo all'ordinamento parziale delle sottosequenze di elementi rimasti non ordinati, fino al loro esaurimento.
Quick Sort
void sort(int[] array, int begin, int end) { int pivot, l, r; if (end > begin) { pivot = array[begin]; l = begin + 1; r = end+1; while (l < r) { if (array[l] < pivot) l++; else { r--; swap(array[l], array[r]); }
Quick Sort
l--; swap(array[begin], array[l]); sort(array, begin, l); sort(array, r, end); } }
Swap
Scambia x con y e viceversa. Parametri passati per riferimento.
void swap(int & x, int & y) { int temp=x; x=y; y=temp; }
Complessit
Caso peggiore vettore ordinato in modo inverso: - O(n2)
Caso migliore/medio: - O(n log2 n)
Merge Sort
Merge Sort
Il merge sort un algoritmo di ordinamento molto intuitivo e abbastanza rapido, che utilizza un processo di risoluzione ricorsivo.
L'idea alla base del merge sort il procedimento Divide et Impera, che consiste nella suddivisione del problema in sottoproblemi via via pi piccoli.
Il merge sort opera quindi dividendo l'insieme da ordinare in due met e procedendo all'ordinamento delle medesime ricorsivamente. Quando si sono divise tutte le met si procede alla loro fusione (merge appunto) costruendo un insieme ordinato.
Due fasi
Fase 1: divide - L'insieme di elementi viene diviso in 2 met. Se l'insieme
composto da un numero dispari di elementi, viene diviso in 2 sottogruppi dei quali il primo ha un elemento in meno del secondo.
Fase 2: impera - Supponendo di avere due sequenze gi ordinate. Per unirle,
l'algoritmo mergesort estrae ripetutamente il minimo delle due sequenze in ingresso e lo pone in una sequenza in uscita.
Merge
void merge (int[] a, int left, int center, int right) int i = left, j=center + 1,k=0; int[] b; while ((i
Merge Sort
void mergesort (int[] a, int left, int right) { int center; if (left < right) { center = (left + right) / 2; mergesort(a, left, center); mergesort(a, center+1, right); merge(a, left, center, right); }
Merge Sort
Complessit: - Caso peggiore O(n log n)
Richiede memoria aggiuntiva per O(n)