Algoritmi di Ordinamento e di Ricerca

Размер: px
Начинать показ со страницы:

Download "Algoritmi di Ordinamento e di Ricerca"

Транскрипт

1 Università degli studi di Messina Facoltà di Ingegneria Corso di Laurea in Ingegneria Informatica e delle Telecomunicazioni Fondamenti di Informatica II Algoritmi di Ordinamento e di Ricerca

2 Introduzione Ordinare una sequenza di informazioni significa effettuare una permutazione in modo da rispettare una relazione d ordine tra gli elementi della sequenza (p.e. minore o uguale ovvero non decrescente) Input: una sequenza di n numeri < a, a2,..., an > Output: una permutazione degli n elementi < a,..., ' ' ', a2 an > tale che, data una funzione di ordinamento f: f ( a ) f ( a )... f ( a ' ' ' 2 n ) 2

3 Importanza dell ordinamento Uno dei maggiori problemi a cui fare fronte quando si manipolano grosse quantità di informazioni è quello relativo all ordinamento ed al reperimento delle stesse Un buon ordinamento garantisce una maggiore facilità di ricerca di tali informazioni Sia il sistema operativo che i software applicativi devono continuamente effettuare ricerche su insiemi di informazioni e quindi l efficienza degli algoritmi di ordinamento usati è un fattore critico per garantire le buone prestazioni del sistema 3

4 Elemento di Informazione In genere tutti gli elementi di informazione della sequenza hanno la stessa struttura Le struttura dell elemento è in genere complessa e viene vista come un insieme di campi di informazione Per esempio la struttura di un elemento della sequenza di elementi di una rubrica telefonica è: Struttura: nome - cognome - numero 4

5 Campi chiave L ordinamento di una sequenza viene fatto scegliendo almeno un campo, definito chiave, che è quello utilizzato per la ricerca nella sequenza. In pratica ricerchiamo le informazioni di tutto l elemento utilizzando una parte nota di esso, la chiave È molto comune la ricerca per più di un campo (chiavi multiple) Le chiavi vanno scelte in modo da ridurre le possibili omonimie Ad esempio nella rubrica cerchiamo principalmente per cognome e poi per nome L ordinamento è quindi spesso effettuato su più di un campo: chiave primaria, secondaria, ecc. 5

6 Esempio. Rossi Paolo Rossi Carlo Bianchi Agata Considerando lo scopo applicativo, la sequenza va ordinata per cognome e nome, in ordine non decrescente. Si ottiene così:. Bianchi Agata Rossi Carlo Rossi Paolo

7 Operazioni Elementari Si nota come siano necessarie operazioni di: Confronto Scambio Risulta inoltre intuitivo come possa essere necessario scandire più volte, magari su sottoinsiemi via via più piccoli la sequenza informativa 7

8 Valutazione degli algoritmi di ordinamento I criteri generali per valutare un algoritmo di ordinamento sono: Complessità computazionale Caso migliore Caso medio Caso peggiore Esibizione di un comportamento naturale Comportamento nel caso di elementi con chiave uguale (stabilità) 8

9 Complessità computazionale È importante avere un indicatore di confronto tra i vari algoritmi possibili di ordinamento, indipendentemente dalla piattaforma hw/sw e dalla struttura dell elemento informativo La complessità computazionale si basa sul numero di operazioni elementari necessarie Si misura come funzione del numero n di elementi della sequenza Gli algoritmi di ordinamento interno si dividono in: Algoritmi semplici - complessità O(n 2 ) Algoritmi evoluti - complessità O(n*log(n)) 9

10 Performance di esecuzione È sempre indipendente dalla piattaforma hw/sw, ma dipende dalla struttura dell elemento informativo e dal numero di chiavi usate: Scambiare tra loro due integer a 32 bit è molto meno oneroso che scambiare due struct complesse Confrontare solo una chiave è meno oneroso che confrontare due chiavi 0

11 Indici delle sequenze Per migliorare la performance di esecuzione è utile costruire un vettore ausiliare (indice) che contiene i puntatori agli elementi della sequenza. I confronti verranno fatti sempre sugli elementi della sequenza ma lo scambio viene fatto sulla sequenza dei puntatori

12 Ordinamenti interni ed esterni Vi sono due diverse categorie di algoritmi di ordinamento: algoritmi che ordinano oggetti ad accesso casuale, come gli array, e algoritmi che ordinano oggetti sequenziali, quali file su disco. Si possono, quindi, distinguere: Ordinamenti interni: sono fatti su sequenze in memoria centrale Ordinamenti esterni: sono fatti su sequenze in memoria di massa 2

13 Ipotesi semplificativa Supporremo che la sequenza di informazioni sia rappresentabile come vettore di n elementi, ovvero ogni elemento sia individuabile tramite un indice variabile da 0 a n-. Gli elementi del vettore potranno essere tipi scalari (integrali o virgola mobile) o aggregati (struct) Il vettore può essere allocato staticamente o dinamicamente 3

14 Classi di algoritmi di ordinamento Vi sono tre metodi generali per ordinare i vettori: scambio (bubble sort, quick sort) selezione (selection sort) inserimento (insertion sort, shell sort) 4

15 Bubble Sort Si tratta di un algoritmo semplice. È un algoritmo di scambio. Il nome deriva dalla analogia dei successivi spostamenti che compiono gli elementi dalla posizione di partenza a quella ordinata simile alla risalita delle bolle di aria in un liquido. Il bubbling si può realizzare in molte versioni basate sullo stesso principio. 5

16 Esempio REGOLA Ad ogni passo si confronta l ultimo elemento con i precedenti scambiandolo nel caso in cui risulti minore passo Si confronta il numero con i precedenti. Essendo il più piccolo risalirà fino alla prima posizione passo Si confronta il numero 2 con i precedenti (escluso il primo elemento) risalendo fino alla seconda posizione passo Si confronta il 7 con l elemento precedente (5): essendo il 7>5 non viene effettuato lo scambio. Sarà invece il 5 a risalire fino alla quarta posizione passo Si confronta il 7 con il 9 scambiando gli elementi passo A questo punto il vettore risulta ordinato 6

17 Descrizione informale Si consideri un vettore di n elementi. Si vuole ordinare in ordine non decrescente Facciamo risalire le bolle dal fondo Sono necessarie diverse scansioni del vettore (iterazioni) Inizializziamo a 0 il flag ordinato (ipotizziamo il vettore disordinato) Scriviamo un ciclo for che controlla le n- iterazioni necessarie ma che termina se il flag ordinato è, con ciò indicando che la precedente iterazione intermedia ha già ordinato il vettore 7

18 Descrizione informale (cont.) La prima iterazione (i=0) si applica a tutto il vettore (n elementi) e posiziona correttamente il primo elemento. La seconda iterazione si applica a tutto il vettore escluso il primo elemento (n- elementi). L i-esima iterazione si applica al sottovettore residuo, in quanto i primi i elementi sono già stati ordinati. L ultima iterazione (i=n-2) si applica agli ultimi due elementi del vettore. Se durante la generica iterazione c è uno scambio, settiamo a 0 il flag ordinato, in modo che il for esterno che controlla le iterazioni sia informato che il vettore non può ancora essere considerato ordinato. 8

19 Descrizione informale (cont.) In ogni scansione, iniziamo puntando l indice all ultimo elemento del vettore e lo confrontiamo col precedente. Se l ultimo elemento è minore dobbiamo scambiarlo con il penultimo. Se c è lo scambio, poniamo a 0 il flag ordinato (indichiamo così che c e stato uno scambio ed il vettore non potrà essere considerato ordinato alla fine della iterazione corrente). Quindi il for interno di controllo verifica se deve fare un successivo confronto; in tal caso l indice risale di una posizione. Per esempio nel secondo ciclo si confronta il penultimo con il terzultimo. 9

20 Codice del Bubble Sort #include <stdio.h> #include <alloc.h> void scambia(int ve[], int i, int j) { int tmp=ve[i]; ve[i]=ve[j]; ve[j]=tmp; void BubbleSort(int v[], int n) { int ordinato,i,j; ordinato=0; for (j=0;j<n- &&!ordinato;j++) { ordinato=; for (i=n-;i>j;i--) { if (v[i]<v[i-]) { scambia(v,i,i-); ordinato=0; 20

21 Codice del Bubble Sort (cont.) void main() { //algoritmo bubble sort //con allocazione dinamica di un vettore di //interi int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do { printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++) { printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); BubbleSort (p,n); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 2

22 Complessità del Bubble Sort L algoritmo BubbleSort esegue alla prima iterazione al più n- confronti/scambi. Alla seconda iterazione n-2 confronti/scambi Le iterazioni sono in totale al più n- Il numero totale al più di confronti/scambi è: (n-)+(n-2)+ + ovvero: n K n = i= n n i= 2 e quindi la complessità risulta: T n =O n 2 22

23 Selection Sort Si tratta di un algoritmo semplice È un algoritmo di selezione Si seleziona l elemento con il valore più basso e lo si scambia con il primo elemento Fra i rimanenti n- elementi si trova l elemento con la chiave più piccola e lo si scambia con il secondo Si procede fino allo scambio degli ultimi due elementi 23

24 Esempio REGOLA Ad ogni passo si seleziona l elemento minore e lo si scambia con il primo elemento non ordinato passo Si seleziona l elemento minore (il sesto che ha valore ) e lo si scambia con l elemento nella prima posizione passo 2 passo 3 passo Si seleziona (tra tutti gli elementi escluso il primo) l elemento minore (il 2) e lo si scambia con l elemento in seconda posizione Si seleziona tra i 4 elementi rimasti il più piccolo (il 3) e lo si scambia con l elemento in terza posizione Si seleziona il 5 e lo si scambia con il 7 passo Si scambiano gli ultimi due elementi passo A questo punto il vettore risulta ordinato 24

25 Codice del Selection Sort #include <stdio.h> #include <alloc.h> void SelectionSort(int *v, int dim) { int i,j,k,elem; int scambia; for (i=0;i<dim-;i++) { scambia=0; k=i; elem=v[i]; for (j=i+;j<dim;j++) { if (v[j]<elem) { k=j; elem=v[j]; scambia=; if(scambia){ v[k]=v[i]; v[i]=elem; void main() { int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do { printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore dall'heap p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++) { printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); SelectionSort (p,n); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 25

26 Complessità del Selection Sort Il ciclo esterno verrà eseguito n- volte Il ciclo interno viene eseguito una media di ½ n volte Il risultato è che l algoritmo di selezione richiede ½ (n 2 -n) selezioni/scambi quindi: T n =O n 2 Il tempo di esecuzione dipende solo in modo modesto dal grado di ordinamento della struttura Nonostante il numero di confronti sia uguale al numero di confronti effettuati nel Bubble Sort, il numero di scambi dell algoritmo Selection Sort risulta essere molto inferiore; ciò lo rende preferibile nel caso di ordinamento di strutture estremamente grandi con chiavi molto piccole. 26

27 Insertion Sort Si tratta di un algoritmo semplice È un algoritmo di inserimento L algoritmo ordina innanzitutto i primi due elementi dell array Quindi si inserisce il terzo elemento nella posizione corretta rispetto ai primi due elementi Il processo continua fino all inserimento (e quindi all ordinamento) di tutti gli elementi 27

28 Esempio REGOLA Si ordinano i primi due elementi dopodiché si inseriscono ad uno ad uno gli altri in maniera ordinata passo Si ordinano i primi due elementi che in tal caso risultano già ordinati passo Si seleziona il terzo elemento (il 5) e lo si inserisce in maniera ordinata nel vettore composto dai primi due elementi passo 3 passo Si seleziona il quarto elemento (il 4) e lo si inserisce in maniera ordinata nel vettore composto dai primi tre elementi Si inserisce il quinto elemento passo Si inserisce l ultimo elemento passo A questo punto il vettore risulta ordinato 28

29 Codice dell Insertion Sort #include <stdio.h> #include <alloc.h> void InsertionSort(int *v, int dim) { int i,j,elem; for (i=;i<dim;i++) { elem=v[i]; for (j=i-;(j>=0) && (elem<v[j]);j--) v[j+]=v[j]; v[j+]=elem; void main() { int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do { printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore dall'heap p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++) { printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); InsertionSort (p,n); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 29

30 Complessità dell Insertion Sort A differenza del Bubble Sort e del Selection Sort, il numero di confronti che avvengono con l Insertion Sort dipende dal livello di ordinamento iniziale del vettore. Se il vettore è ordinato, il numero di confronti è pari a n-, altrimenti i confronti sono dell ordine di n 2 In generale, nei casi peggiori, l Insertion Sort, non è più efficiente del Bubble Sort e del Selection Sort, mentre nei casi medi è solo leggermente più veloce Nonostante il numero di confronti (in alcuni casi) sia molto basso gli elementi del vettore devono essere traslati ogniqualvolta che un elemento viene inserito nella posizione corretta. Ciò rende il numero di spostamenti molto alto quindi: T n =O n 2 I vantaggi dell Insertion Sort sono dovuti al fatto che esso si comporta in maniera naturale (manipola di più i vettori disordinati e di meno quelli ordinati). Esso va quindi usato nel caso di elenchi quasi ordinati. 30

31 Shell Sort Si tratta di un algoritmo evoluto Deve il suo nome al suo ideatore D. L. Shell È un algoritmo di inserimento Il metodo di ordinamento si basa sulla riduzione degli incrementi Si confrontano tutti gli elementi che si trovano ad una distanza d e si continua riducendo il valore di d fino ad arrivare agli elementi adiacenti (d=) 3

32 Esempio passo confronti scambi REGOLA Si confrontano gli elementi distanti d, scambiandoli nel caso non siano ordinati. Quindi vengono ordinati gli elementi diminuendo il valore di d fino ad arrivare ad. In questo esempio si sono scelti valori di d pari a: 3,2, Si confrontano gli elementi distanti tre posizioni scambiandoli nel caso il primo sia maggiore del secondo passo Si confrontano gli elementi distanti 2 posizioni ( e ) riordinandoli ( e ) passo Adesso si riduce la distanza ad uno e si confrontano gli elementi adiacenti, eventualmente scambiandoli passo A questo punto il vettore risulta ordinato 32

33 Considerazioni Sebbene lo Shell Sort sia facile da capire intuitivamente, una sua analisi formale risulta difficile In particolare, la valutazione dei valori ottimali della distanza d (detta spaziatura) sfugge ai teorici Si possono usare diverse spaziature per implementare lo Shell Sort. Di solito si ordina l array con una spaziatura grande, si riduce la spaziatura, e si riordina l array L unico vincolo da rispettare è che nell ultimo passo la spaziatura valga uno Ad esempio, la sequenza 9,5,3,2, funziona molto bene Sono da evitare le sequenze formate dalle potenze di 2 che, per complessi motivi matematici, riducono l efficienza dell algoritmo (pur conservandone l efficacia) 33

34 Codice dello Shell Sort #include <stdio.h> #include <alloc.h> void ShellSort(int * vett, int dim) { int i,j,gap,k; int x, a[5]; a[0]=9;a[]=5;a[2]=3;a[3]=2;a[4]=; for (k=0;k<5;k++){ gap=a[k]; for(i=gap;i<dim;i++){ x=vett[i]; for(j=i-gap;(x<vett[j]) && (j>=0); j=j-gap) vett[j+gap]=vett[j]; vett[j+gap]=x; void main() { int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do { printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore dall'heap p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++) { printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); ShellSort (p,n); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 34

35 Complessità dello Shell Sort L algoritmo Shell Sort risulta essere migliore, in termini di prestazioni, degli algoritmi semplici (Bubble Sort, Selection Sort, Insertion Sort) Intuitivamente, tale miglioramento deriva dal fatto che lo Shell Sort sposta velocemente gli elementi nelle loro destinazioni La complessità media è O(n.25 ), mentre quella del caso peggiore diventa O(n.5 ) quindi: T n =O n,2 mediamente T n =O n,5 caso peggiore 35

36 Quick Sort Si tratta di un algoritmo evoluto che ha complessità computazionale O(n)=n*log(n) È un algoritmo di scambio È un algoritmo ricorsivo Ricordiamo che la ricorsione consiste nell esprimere F(n) in funzione di F(n-) ed inoltre nel conoscere il valore iniziale F(0) Gli algoritmi ricorsivi sono più semplici ed eleganti, ma la loro esecuzione comporta, a causa della annidarsi della funzione che si richiama da se un uso a volte esagerato dello stack È anche disponibile un implementazione in ANSI-C di qsort, una funzione C standard di libreria che viene tipicamente implementata con il quicksort. Le chiamate ricorsive sono state sostituite da operazioni dirette sullo stack 36

37 Approccio informale Si consideri un vettore di n elementi e lo si ordini con algoritmi semplici, con un tempo di calcolo proporzionale a n 2. Si supponga, invece di dividere il vettore da ordinare in due sottovettori di n/2 elementi ciascuno e di ordinare le due metà separatamente. Applicando sempre gli algoritmi non evoluti, si avrebbe un tempo di calcolo pari a (n/2) 2 + (n/2) 2 =n 2 /2. Se riunendo i due sottovettori ordinati si potesse riottenere il vettore originario tutto ordinato avremmo dimezzato il tempo di calcolo Se questo ragionamento si potesse applicare anche immaginando una decomposizione del vettore originario in quattro, si avrebbe un tempo di calcolo totale pari a: (n/4) 2 +(n/4) 2 +(n/4) 2 +(n/4) 2 =n 2 /4 Se si potesse dividere in 8, si avrebbe un tempo ancora più basso, e così via dicendo. 37

38 Descrizione L algoritmo Quick Sort si basa sull idea delle partizioni. La procedura generale consiste nella selezione di un valore (detto pivot) e nella suddivisione del vettore in due sezioni. Tutti gli elementi maggiori o uguali al valore del pivot andranno da una parte e tutti i valori minori dall altra. Questo processo viene ripetuto per ognuna delle sezioni rimanenti fino all ordinamento dell intero vettore. 38

39 Esempio i passo passo 2 pivot REGOLA pivot pivot i j i j sezione sezione 2 j Si seleziona l elemento pivot e si spostano gli elementi più piccoli alla sua sinistra e i più grandi alla sua destra. Si suddivide, quindi, il vettore in due sezioni e si procede ricorsivamente Si sceglie il quarto elemento (valore 4 come elemento pivot Si seleziona, partendo dall estremità sinistra, il primo elemento maggiore o uguale del pivot e, partendo dall estremità destra, il primo elemento minore o uguale del pivot. Dopodiché si scambiano e si continua fino alla scansione di tutti gli elementi (i<=j) Si divide il vettore in due sezioni e si procede ricorsivamente sulle due sezioni scegliendo gli elementi pivot passo Si scorrono gli elementi delle due sezioni selezionando e scambiando gli elementi che risultano maggiori (da sinistra) e minori (da destra) dei rispettivi pivot A questo punto il vettore risulta ordinato 39

40 Considerazioni L esempio precedente si riferisce al caso migliore che avviene quando la scelta dell elemento pivot ricade sull elemento mediano del vettore comportando una suddivisione del vettore in sezioni di pari dimensioni Il caso peggiore avviene quando il vettore viene decomposto in due sottovettori, di cui il primo ha dimensione uguale alla dimensione originaria meno, e l altro ha una dimensione unitaria. Il pivot coincide con l elemento massimo del vettore La scelta dell elemento pivot risulta, quindi, essere determinante Se si fosse in grado di risalire all elemento mediano la scelta ricadrebbe su di esso. Normalmente tale operazione comporta una conoscenza a priori sul vettore o un analisi opportuna il cui tempo deve essere preso in considerazione Il metodo più usato rimane quello della scelta casuale dell elemento pivot, selezionando, ad esempio, l elemento che occupa la posizione centrale 40

41 i Esempio - caso peggiore Se scegliamo come pivot l elemento di posto centrale (indice m=(inf+sup)/2), ovvero il 34, questo, casualmente, coincide con pivot l elemento maggiore del vettore pivot i j L indice i viene incrementato fino a quando non viene trovato un elemento più grande o uguale al pivot. Nel nostro esempio l indice i si arresta in corrispondenza del pivot. L esempio mette in evidenza il motivo di incrementare l indice i fino a quando si trova un elemento più grande o uguale al pivot. Se non ci fosse la condizione uguale, nel nostro esempio l indice i verrebbe continuamente incrementato oltre la dimensione del vettore. Per quanto riguarda l indice j esso non viene spostato in quanto l elemento j-esimo è inferiore al pivot. Gli elementi di indice i e j vengono scambiati, e l indice i viene incrementato, mentre j viene decrementato. L indice i viene quindi fatto incrementare fino a quando arriva all elemento 34, che è pari al pivot. L indice j non viene fatto decrementare perché si riferisce ad un elemento già inferiore al pivot Siccome i > j, la prima passata è finita: otteniamo le seguenti sezioni sezione sezione 2 4

42 Esempio - caso peggiore (cont.) Come si vede l esempio considerato rappresenta un caso peggiore, perché il vettore originario è stato decomposto in due vettori di cui il primo (quello compreso tra inf e j) ha dimensione quasi uguale a quella originaria. E chiaro che la complessità di riordino del primo sottovettore è praticamente la stessa di quella relativa al riordino del vettore originario. Dunque non si è avuto alcun vantaggio nel suddividere il vettore. 42

43 Codice del Quick Sort int partition(int v[], int l, int r){ int i=l-,j=r; int pivot=v[r]; //si piglia come elemento pivot // l'ultimo elemento for(;;){ while(v[++i]<pivot) ; while(v[--j]>pivot) if(j==l) break; if(i>=j) break; scambia(v,i,j); scambia(v,i,r); //mette l'elemento pivot // nella giusta posizione return i; void quicksort(int v[], int l, int r){ int i; if(r<=l) return; i=partition(v,l,r); quicksort(v,l,i-); quicksort(v,i+,r); int main(){ int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do{ printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore dall'heap p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++){ printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); quicksort (p,0,n-); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 43

44 Complessità del Quick Sort Nel caso migliore, siccome l array viene diviso in due ad ogni passo, e l algoritmo deve comunque esaminare tutti gli n elementi, il tempo di esecuzione risulta O(n log(n)). Nel caso peggiore ogni chiamata ricorsiva a quicksort ridurrebbe solo di un unità la dimensione dell array da ordinare. Sarebbero quindi necessarie n chiamate ricorsive per effettuare l ordinamento, portando a un tempo di esecuzione di O(n 2 ). Una soluzione a questo problema si può ottenere scegliendo a caso un elemento come pivot. Questo renderebbe estremamente improbabile il verificarsi del caso peggiore. quindi: T n =O nlog 2 n caso migliore e caso medio T n =O n 2 caso peggiore (estremamente raro) 44

45 Quick Sort -analisi rigorosa L algoritmo è costituito da alcune assegnazioni, un ciclo for e due chiamate ricorsive. Il ciclo for viene eseguito n + volte, quindi con un costo O(n). Se n= la funzione costo è una costante. Se n> bisogna considerare il costo delle chiamate ricorsive. T(n) = O(n) + O() T(k) + T(n - k) n n = > 45

46 Quick Sort -analisi rigorosa (cont.) Caso peggiore Si ha quando il pivot divide l insieme degli elementi in due parti: una composta da un solo elemento e l'altra dagli n- restanti. T(n) = O(n) + T() + T(n ) = = O(n) + O() + T(n-) = = O(n) + O() + O(n -) + O() + T(n-2) = = O(n) + O() + O(n ) + O() + O(n - 2) + O() + T(n-3) generalizzando : T(n) = T(n - k) + k i = O(n -i + ) La ricorsione si chiude quando k=n-. In questo caso, infatti, l'argomento di T() sarà pari ad uno e arriveremo al caso banale T()=O(), quindi: T(n) = T() + = O n i= n - i= O(n - i + ) = (n - i + ) = 2 = O n(n + ) = O(n ) 2 46

47 Quick Sort -analisi rigorosa (cont.) Caso migliore Si ha quando il pivot divide l insieme degli elementi in due parti uguali. T(n) = O(n) + T n = O(n) + 2 O 2 = O(n) + 2 O = O(n) + O(n) + O(n) + 8T generalizzando : T(n) = 2 k n 2 n T k 2 + n 2 + T + + n 2 k i = = n 2T 4 2 O O(n) n 4 = + n 8 2T n 8 = La ricorsione si chiude quando n=2 k. In questo caso, infatti, l'argomento di T() sarà pari ad uno e arriveremo al caso banale T()=O(), quindi: log n 2 T(n) = nt() + O(n) = i= = O(n) + O(n log 2 n) = O(n log 2 n) 47

48 Quick Sort -analisi rigorosa (cont.) Caso medio Tutti gli elementi possono essere presi come pivot con probabilità /n. Anche la generica suddivisione i, n-i avviene con probabilità /n. T(n) = O(n) + = O(n) + n = O(n) + n 2 n n i = n [ T(i) + T(n i) ] i = n i = T(i) + T(i) n n i= T(n i) moltiplicando entrambi i membri per n si ottiene: nt(n) = no(n) + 2 (n -)T(n -) = n i= che scritta per n- diventa: T(i) (n )O(n-) + 2 n 2 i= = T(i) sottraendo membro a membro: nt(n) = (n + )T(n ) + 2O(n) dividendo entrambi i membri per n(n+): T(n) T(n -) 2 = + = n + n O(n + ) = [...] T(n - 2) n - T(2) = quindi si ottiene: n 2 2 dx = i= 3 2 O(n) 2 i = O(n + ) n i= i T (n) = n x 2 ln(n) O(n ln(n)) 48

49 Merge Sort Si tratta di un algoritmo evoluto che ha complessità computazionale O(n)=n*log(n) anche nel caso peggiore A differenza del Quick Sort è un algoritmo stabile È un algoritmo ricorsivo Si basa sul principio divide et impera sfruttando il concetto di fusione (merging) di array ordinati 49

50 Il merging a 2 vie - esempio A(N) B(M) 4 8 REGOLA Ad ogni passo si seleziona l'elemento più piccolo tra i due elementi di posto inferiore degli array e si inserisce nell'array di uscita C(N+M) passo passo passo passo passo passo passo

51 Il merging a 2 vie codice Tale implementazione necessita di un terzo array (di dimensione pari alla somma delle dimensioni degli array di partenza) per contenere l'output. void mergeab(int c[], int a[], int N, int b[], int M){ int i,j,k; for(i=0,j=0,k=0;k<n+m;k++){ if(i==n){ c[k]=b[j++]; continue; if(j==m){ c[k]=a[i++]; continue; c[k] = (a[i]<b[j])? a[i++] : b[j++]; 5

52 Merging astratto sul posto Tale implementazione utilizza ancora un array ausiliario di dimensione proporzionale all'output, ma è più efficiente perchè evita di effettuare i test sulla fine degli array. Per fare ciò il secondo array viene trascritto in maniera inversa alla fine del primo. void merge(int a[], int l, int m, int r){ int i,j,k,*aux; aux=(int*)malloc((r-l+)*sizeof(int)); for(i=m+;i>l;i--) aux[i-]=a[i-]; for(j=m;j<r;j++) aux[r+m-j]=a[j+]; for(k=l;k<=r;k++) if(aux[j]<aux[i]) a[k]=aux[j--]; else a[k]=aux[i++]; 52

53 53 Merge Sort - descrizione Per ordinare un dato array è sufficiente dividerlo in due, ordinare (ricorsivamente) le due metà e fondere le sequenze ordinate risultanti. La condizione di uscita della ricorsione si ha quando gli array hanno una dimensione pari a uno. REGOLA divisione fusione

54 Codice del Merge Sort int main(){ void mergesort(int a[], int l, int r){ if(r<=l) return; int m=(r+l)/2; mergesort(a,l,m); mergesort(a,m+,r); merge(a,l,m,r); int n,i, *p; //acquisizione da tastiera del numero degli //elementi del vettore do{ printf("quanti elementi deve avere il vettore?:"); scanf("%d",&n); while (n<2 n>50); //allocazione degli n elementi del vettore dall'heap p=(int*)malloc(n*sizeof(int)); //acquisizione degli elementi del vettore for (i=0;i<n;i++){ printf("immetti il valore dell'elemento %d del vettore. V[%d]=",i,i); scanf("%d",p+i); mergesort (p,0,n-); //visualizza il vettore ordinato for (i=0;i<n;i++) printf("v[%d]=%d\n",i,*(p+i)); getchar(); 54

55 Proprietà del Merge Sort Il Merge Sort richiede all'incirca Nlog 2 N confronti per ordinare un qualunque file di N elementi Il Merge Sort utilizza uno spazio ausiliario proporzionale a N Il Merge Sort è stabile, se il merging su cui si basa è stabile Le risorse di tempo e spazio impiegate dal Merge Sort non dipendono dall'ordinamento iniziale del file di input 55

56 Ordinamento di strutture complesse Finora si è parlato solo dell ordinamento di array di interi. Ovviamente è possibile ordinare array di un qualunque tipo di dati, semplicemente cambiando il tipo dei parametri e delle variabili della funzione di ordinamento I programmi applicativi che richiedono un ordinamento, in genere, organizzano gruppi di dati più complessi Ad esempio gli elenchi di indirizzi, gli archivi per inventari e le registrazioni contengono raccolte di dati che, nei programmi C, vengono normalmente raccolte all interno di strutture Anche se in genere una struttura contiene numerosi membri, deve essere ordinata sulla base di un solo membro utilizzato come chiave dell ordinamento Ad eccezione della scelta della chiave, anche per l ordinamento di strutture si impiegano le tecniche già viste per gli altri tipi di dati 56

57 Algoritmi di ordinamento esterno L algoritmo di ordinamento si complica notevolmente quando si trattano strutture dati complesse e articolate, quali file o archivi. Il problema è legato alla dimensione, in termini di occupazione di memoria, della struttura in questione: il metodo più semplice, efficace e veloce per ordinare tale struttura è trasferirla interamente in memoria e ivi ordinarla, ma spesso le dimensioni non consentono questo tipo di operazione. Memoria centrale f ordinato File f Alg. ord. File f Memoria di massa f non ordinato 57

58 KeySort Una tecnica che consente, in alcuni casi, di superare il problema è quella del keysort. Essa consiste nel creare una struttura in memoria, tipicamente un vettore, contenente il campo chiave del record che costituisce l unità di informazione. Inoltre bisogna memorizzare la posizione iniziale del record all interno del file. L ordinamento verrà fatto in memoria su tale struttura ed infine le modifiche verranno riportate nel file. Key Pos Key Pos File f disordinato KeySort File f ordinato Memoria di massa Memoria centrale 58

59 KeySort: valutazioni Non sempre questa tecnica risolve il problema: nei casi in cui il record è composto dalla sola chiave, non si trae alcun vantaggio utilizzando il keysort, anzi, la struttura in memoria centrale è più pesante di quella in memoria di massa, dovendo memorizzare l informazione supplementare relativa alla posizione del record nel file; la tecnica si rivela insufficiente anche quando, pur trattandosi di record complessi e strutturati, il vettore chiavi-indici assume una dimensione tale da non poter essere contenuta in memoria; altro problema è relativo alla scrittura del file ordinato: il metodo più semplice implica la creazione di un nuovo file nel quale scrivere gli elementi secondo l ordine specificato nel vettore; ciò non sempre è possibile limitatamente alle capacità del dispositivo di memorizzazione di massa. L alternativa consiste nel leggere un dato file, ricercarlo nel vettore in memoria centrale, risalire alla nuova posizione attraverso il campo pos, leggere dal file l elemento nella posizione in cui andrà scritto il primo dato (pos) e dunque riscriverlo nella nuova posizione. Tutto ciò si traduce in un notevole dilatamento dei tempi di esecuzione. 59

60 Sort Merge La soluzione ai problemi elencati, è, come anticipato, quella di scomporre il file in un certo numero di parti, da ordinare in memoria centrale, e dunque fondere tali parti ordinate in un unico file ordinato. La tecnica utilizzata è nota in letteratura col nome Sort Merge, che, non a caso, richiama alla memoria l algoritmo di ordinamento Merge Sort, dal quale si ispira: la differenza è che nel secondo caso si suddivide il vettore fino ad arrivare a vettori di un solo elemento e solo allora comincerà l operazione di fusione tra questi, mentre nell algoritmo Sort Merge la suddivisione del file produrrà un certo numero di piccoli sottoinsiemi di n elementi detti run, che verranno ordinati in memoria centrale e dunque fusi. file run 60

61 Sort Merge bilanciato a P vie Si supponga di avere: N record da ordinare su un dispositivo esterno Spazio in memoria centrale per memorizzare M record 2P dispositivi esterni a disposizione durante l'ordinamento Assegniamo l'etichetta 0 al dispositivo esterno contenente l'input e le etichette, 2,..., 2P-agli altri dispositivi. L'obiettivo dell'algoritmo è quello di riscrivere i record nel dispositivo 0, in modo ordinato. 6

62 L algoritmo. Il file iniziale viene suddiviso fra i dispositivi di input P, P+,..., 2P -, in blocchi ordinati di M record ciascuno (tranne eventualmente il blocco finale, che sarà più piccolo se N non è multiplo di M). 2. Dopo questa fase di distribuzione, il numero di blocchi ordinati su ciascun dispositivo è pari a N/(MP) arrotondato all'intero precedente o successivo. 3. Nel primo passaggio si considerano i dispositivi da P a 2P- come dispositivi di input e quelli da 0 a P-come dispositivi di output. 4. Si esegue un merging a P vie per fondere i blocchi ordinati di dimensione M sui dispositivi di input in blocchi ordinati di dimensione PM, e quindi si distribuiscono fra i dispositivi di output. 5. Dopo questa fase, il numero di blocchi ordinati su ciascun dispositivo sarà N/(P 2 M) 6. Si itera il processo eseguendo un secondo passaggio di merging considerando i dispositivi da 0 a P- come dispositivi di input e quelli da P a 2P- come dispositivi di output. 7. Continuando in questo modo, andando avanti e indietro fra i dispositivi 0,..., P- e i dispositivi P,..., 2P-, si aumenta la dimensione dei blocchi di un fattore P fino a ottenere, prima o poi, un solo blocco ordinato sul dispositivo 0 o sul dispositivo P. 62

63 Esempio P=3 M=3 N=45 0 asortingandmergingexamplewithfortyfiverecords aos dmn aex fht erv irt egr lmp ort ceo agn gin eiw fiy drs 3 4 aadeeegggiiilmmnnnoprrstwx cdeeffhioorrrsttvy 0 2 aaginorst ffhiortty deggimnnr cdeeorrsv aeeilmpwx 0 aacddeeeeeffggghiiiilmmnnnoooprrrrrsstttvwxy 63

64 Caso ideale Ciascun file (dispositivo esterno) contiene un run È sufficiente solo una merge phase Sfortunatamente è di difficile realizzazione Ci vorrebbero tanti file quanti sono i run, ma poiché il numero di file gestibili da programma è limitato, la condizione non sempre è realizzabile. 64

65 Complessità Al fine di calcolare la complessità degli algoritmi di ordinamento esterno si assume che il costo delle operazioni di read e write sui dispositivi esterni sia molto maggiore rispetto alle operazioni primitive eseguite in memoria centrale. Quindi viene totalmente ignorato il costo di un ordinamento se è eseguito interamente nella memoria centrale. Avendo 2P dispositivi esterni e memoria centrale sufficiente a ospitare M record, un Sort Merge basato su un merge bilanciato a P vie richiede all'incirca un numero di passaggi pari a: log p N / M Un passaggio è richiesto per la distribuzione sui dispositivi. Se N=MP K, i blocchi sono tutti di dimensione MP dopo la prima fusione, MP 2 dopo la seconda, MP 3 dopo la terza, e così via. L'ordinamento si completa dopo k=log P (N/M) passaggi. Altrimenti, se MP K- <N<MP K, l'effetto di blocchi incompleti o vuoti rende i blocchi di dimensione molto variabile verso la fine del processo. Comunque, il processo termina sempre dopo k=log P (N/M) passaggi. 65

66 Complessità (cont.) Ad esempio, se vogliamo ordinare miliardo di record usando 6 dispositivi e memoria interna sufficiente a contenere milione di record, possiamo eseguire un Sort Merge a 3 vie per un totale di 8 passaggi sui dati ( per la distribuzione iniziale e log 3 000=7 per il merging). Avremo sequenze ordinate di milione di record dopo il passo di distribuzione iniziale, di 3 milioni di record dopo la prima fusione, di 9 milioni di record dopo la seconda fusione, di 27 milioni di record dopo la terza fusione, ecc. In pratica la decisione più importante da prendere nel Sort Merge riguarda la scelta del valore P, cioè il numero di vie del merging. Accesso sequenziale -> P deve essere pari alla metà dei dispositivi Accesso non sequenziale -> è possibile aumentare P diminuendo il numero di passi, ma ciò farà crescere il numero di accessi 66

67 Sort Merge polifase Svantaggio del merging bilanciato a P vie: usa attivamente solo circa la metà dei dispositivi durante il merging L'idea di base del Sort Merg polifase è quella di distribuire i blocchi ordinati prodotti dalla selezione con sostituzione in modo un pò disuguale fra i dispositivi a disposizione (lasciandone uno vuoto), e quindi di applicare una strategia del tipo fondi finchè non è vuoto * 7* 4* 6* 3* 4*3 2* * 2*3 2*5 *3 *5 *9 *7 67

68 Sort Merge polifase (cont.) Si dimostra che l'efficienza dell'algoritmo è maggiore se la distribuzione dei blocchi ordinati avviene secondo la distribuzione di Fibonacci:,,2,3,5,8,3,2,... Tale metodo consente di eseguire lo stesso lavoro con circa la metà dell'hardware. Se il numero di dispositivi esterni è fissato, il merging polifase risulta sempre più efficiente del merging bilanciato. 68

69 Ricerca I database consentono ad un utente di ricercare un record sulla base di una chiave Per ricercare le informazioni in una struttura dati (ad esempio un array) esistono due metodi a seconda che la struttura dati sia ordinata o no Ricerca sequenziale: opera su strutture dati non ordinate Ricerca binaria : opera su strutture dati ordinate I compilatori C forniscono la funzione bsearch() nell ambito delle funzioni di libreria standard 69

70 Ricerca sequenziale Per trovare le informazioni in un array non ordinato è necessario eseguire una ricerca sequenziale che parte dal primo elemento e termina nel momento in cui viene trovata una corrispondenza o alla fine dell array Questo metodo deve essere necessariamente utilizzato su tutti i dati non ordinati ma può essere impiegato anche quando i dati sono ordinati int sequential_search (int * v, int dim, int key){ int i; for(int i=0;i<dim;i++) if (key==v[i]) return i; return -; /*elemento non trovato*/ 70

71 Tempo di Ricerca della Ricerca Sequenziale Nel caso migliore, la ricerca sequenziale, deve verificare un solo elemento e nel caso peggiore deve controllare tutti gli n elementi È facile comprendere che una ricerca sequenziale richiederà, in media, il controllo di n/2 elementi. quindi: T n =O n 2 mediamente 7

72 Ricerca Binaria Se i dati sono ordinati la ricerca può essere eseguita impiegando un metodo migliore Si controlla l elemento centrale Se è maggiore rispetto alla chiave si eseguirà la ricerca sulla prima metà del vettore se no sulla seconda Si deve ripetere questa procedura fino a trovare l elemento o finché non vi saranno più elementi da cercare Esempio Si vuole trovare il 4 nell array seguente Si legge il valore centrale (5) e poiché risulta maggiore della chiave (4) si continua la ricerca sulla prima metà Ora l elemento centrale è 3 che risulta minore della chiave e quindi la prima metà viene scartata La ricerca continua e viene trovato l elemento cercato 72

73 Codifica della Ricerca Binaria int binary_search (int * v, int dim, int key){ int low,high,mid; low=0; high=dim-; while(low<=high){ mid=(low+high)/2; if(key<v[mid]) high=mid-; else if (key>v[mid]) low=mid+; else return mid; /*trovato*/ return -; /*elemento non trovato*/ Per applicare questa funzione ad altre strutture di dati basta modificare la parte di confronto della routine 73

74 Tempo di Ricerca della Ricerca Binaria Nella ricerca binaria il numero di confronti nel caso peggiore è pari a: log 2 n In un caso medio il numero di confronti sarà minore Nel caso migliore è richiesto un solo confronto quindi: T n =O log 2 n caso peggiore 74

Fondamenti di Informatica

Fondamenti di Informatica Algoritmi di ordinamento Gli ordinamenti interni sono fatti su sequenze in memoria centrale Fondamenti di Informatica 18. Algoritmi di ordinamento in C++ Gli ordinamenti esterni sono fatti su sequenze

Подробнее

Corso di Tecniche di Programmazione

Corso di Tecniche di Programmazione Problema: Data una sequenza di elementi in ordine qualsiasi, ordinarla. Corso di Tecniche di Programmazione Corsi di Laurea in Ingegneria Informatica ed Automatica Anno Accedemico 003/004 Proff. Giuseppe

Подробнее

Corso di Fondamenti di Informatica

Corso di Fondamenti di Informatica Corso di Fondamenti di Informatica Gli algoritmi di base sul tipo array: ordinamento e ricerca Claudio De Stefano - Corso di Fondamenti di Informatica 1 Algoritmi di ordinamento gli algoritmi si differenziano

Подробнее

Algoritmi di ordinamento: Array e ricorsione

Algoritmi di ordinamento: Array e ricorsione Laboratorio di Algoritmi e Strutture Dati Aniello Murano http://people.na.infn.it people.na.infn.it/~murano/ 1 Algoritmi di ordinamento: Array e ricorsione 2 1 Indice Algoritmi di ordinamento: Insertion

Подробнее

A. Ferrari Algoritmi notevoli

A. Ferrari Algoritmi notevoli Algoritmi notevoli in linguaggio C algoritmi o o o ricerca (verificare la presenza di un valore in un array) o o o ricerca sequenziale (array non ordinato) ricerca sequenziale (array ordinato) ricerca

Подробнее

Fondamenti di Informatica. Algoritmi di Ricerca e di Ordinamento

Fondamenti di Informatica. Algoritmi di Ricerca e di Ordinamento Fondamenti di Informatica Algoritmi di Ricerca e di Ordinamento 1 Ricerca in una sequenza di elementi Data una sequenza di elementi, occorre verificare se un elemento fa parte della sequenza oppure l elemento

Подробнее

Laboratorio di Programmazione Appunti sulla lezione 4: Divide et impera e algoritmi di ordinamento

Laboratorio di Programmazione Appunti sulla lezione 4: Divide et impera e algoritmi di ordinamento Laboratorio di Programmazione Appunti sulla lezione 4: Divide et impera e algoritmi di ordinamento Alessandra Raffaetà Università Ca Foscari Venezia Corso di Laurea in Informatica Ricerca binaria Assunzione:

Подробнее

Gli algoritmi ricorsivi di ordinamento. Paolo Camurati Dip. Automatica e Informatica Politecnico di Torino

Gli algoritmi ricorsivi di ordinamento. Paolo Camurati Dip. Automatica e Informatica Politecnico di Torino ordinamento Paolo Camurati Dip. Automatica e Informatica Politecnico di Torino Merge Sort Ricorsivo, divide et impera Stabile Divisione: due sottovettori SX e DX rispetto al centro del vettore. p r A.A.

Подробнее

A. Ferrari. algoritmi notevoli. Python. Alberto Ferrari Informatica

A. Ferrari. algoritmi notevoli. Python. Alberto Ferrari Informatica algoritmi notevoli Python algoritmi o ricerca (verificare la presenza di un valore in una sequenza) o o o ricerca sequenziale (sequenza non ordinata) ricerca sequenziale (sequenza ordinata) ricerca binaria

Подробнее

Sommario. Ordinamento. Selection Sort Bubble Sort/ Shaker Sort Shell Sort

Sommario. Ordinamento. Selection Sort Bubble Sort/ Shaker Sort Shell Sort Ordinamento Sommario Ordinamento Selection Sort Bubble Sort/ Shaker Sort Shell Sort Cosa e' l'ordinamento Il problema consiste nell elaborare insiemi di dati costituiti da record I record hanno sono costituiti

Подробнее

Calcolo Parallelo e Distribuito

Calcolo Parallelo e Distribuito Calcolo Parallelo e Distribuito 1 Problema Progettare un algoritmo parallelo per l ordinamento di un vettore su un calcolatore MIMD a memoria distribuita con p processori Sorting Bitonico A. Murli Calcolo

Подробнее

Strutture dati e algoritmi. Sommario

Strutture dati e algoritmi. Sommario Sommario Strutture dati e algoritmi: Ricerca (lineare e binaria) Ordinamento (per selezione) Strutture dati e algoritmi Come esempi concreti di applicazioni in C++ si useranno le strutture dati e gli algoritmi.

Подробнее

Algoritmi di ordinamento

Algoritmi di ordinamento Algoritmi di ordinamento! Selection Sort! Quick Sort! Lower bound alla complessità degli algoritmi di ordinamento Ordinamento 1 Selection Sort SelectionSort(dati[]) { for (i=0; idati.length-1; i++) { min

Подробнее

UNIVERSITÀ DEGLI STUDI DI PAVIA FACOLTÀ DI INGEGNERIA. Matlab: esempi ed esercizi

UNIVERSITÀ DEGLI STUDI DI PAVIA FACOLTÀ DI INGEGNERIA. Matlab: esempi ed esercizi UNIVERSITÀ DEGLI STUDI DI PAVIA FACOLTÀ DI INGEGNERIA Matlab: esempi ed esercizi Sommario e obiettivi Sommario Esempi di implementazioni Matlab di semplici algoritmi Analisi di codici Matlab Obiettivi

Подробнее

SOMMARIO IL PROBLEMA DELLA RICERCA. Algoritmi di ricerca: Algoritmi di ordinamento: RICERCA LINEARE

SOMMARIO IL PROBLEMA DELLA RICERCA. Algoritmi di ricerca: Algoritmi di ordinamento: RICERCA LINEARE SOMMARIO IL PROBLEMA DELLA RICERCA Algoritmi di ricerca: Ricerca lineare; Ricerca binaria (su elenchi già ordinati). Dato un array e un oggetto, stabilire se l oggetto è contenuto in un elemento dell array,

Подробнее

Algoritmi di Ricerca Ordinamento

Algoritmi di Ricerca Ordinamento Algoritmi di Ricerca e Ordinamento Prof. Francesco Accarino IIS Altiero Spinelli Sesto San Giovanni Appunti Di Informatica Prof. Accarino 1 Algoritmi classici In ambito informatico alcuni problemi si presentano

Подробнее

Calcolo Parallelo e Distribuito

Calcolo Parallelo e Distribuito Calcolo Parallelo e Distribuito 1 Problema Progettare un algoritmo parallelo per l ordinamento di un vettore su un calcolatore MIMD a memoria distribuita con p processori Sorting Bitonico A. Murli Calcolo

Подробнее

Divide et impera. Divide et impera. Divide et impera. Divide et impera

Divide et impera. Divide et impera. Divide et impera. Divide et impera Divide et impera Divide et impera La tecnica detta divide et impera è una strategia generale per impostare algoritmi (par. 9.4). Consideriamo un problema P e sia n la dimensione dei dati, la strategia

Подробнее

2. Analisi degli Algoritmi

2. Analisi degli Algoritmi 2. Analisi degli Algoritmi Introduzione 2.1 Un modello di macchina elementare: la Macchina a Registri 2.2 Costo di esecuzione di un programma 2.3 Analisi del costo di esecuzione: il modello a costi uniformi

Подробнее

Algoritmi di ordinamento: Array e ricorsione

Algoritmi di ordinamento: Array e ricorsione Laboratorio di Algoritmi e Strutture Dati Aniello Murano http://people.na.infn.it people.na.infn.it/~murano/ 1 Algoritmi di ordinamento: Array e ricorsione 2 1 Insertion Sort Quicksort Heapsort Indice

Подробнее

PASCAL: I VETTORI TRATTO DA CAMAGNI-NIKOLASSY, CORSO DI INFORMATICA, VOL. 1, HOEPLI. Informatica

PASCAL: I VETTORI TRATTO DA CAMAGNI-NIKOLASSY, CORSO DI INFORMATICA, VOL. 1, HOEPLI. Informatica PASCAL: I VETTORI TRATTO DA CAMAGNI-NIKOLASSY, CORSO DI INFORMATICA, VOL. 1, HOEPLI Informatica I dati strutturati: gli array I vettori (o Array) Fino a ora abbiamo memorizzato le informazioni (valori)

Подробнее

Albero di Riscorsione

Albero di Riscorsione Albero di Riscorsione Albero di ricorsione Un albero di ricorsione è un modo di visualizzare cosa accade in un algoritmo divide et impera L etichetta della radice rappresenta il costo non ricorsivo della

Подробнее

Algoritmi di ordinamento (I parte)

Algoritmi di ordinamento (I parte) Algoritmi di ordinamento (I parte) E2: sommario Classificazione degli algoritmi di ordinamento Studio di due implementazioni di algoritmi che utilizzano interfaccia Comparable Algoritmo per inserimento

Подробнее

Algoritmi di ricerca. Per ricerca si intende qui il procedimento di localizzare una particolare informazione in un elenco di dati.

Algoritmi di ricerca. Per ricerca si intende qui il procedimento di localizzare una particolare informazione in un elenco di dati. E. Calabrese: Fondamenti di Informatica Algoritmi-1 Algoritmi di ricerca Per ricerca si intende qui il procedimento di localizzare una particolare informazione in un elenco di dati. Per esempio: - cercare

Подробнее

Algoritmi di ordinamento in linguaggio C

Algoritmi di ordinamento in linguaggio C Algoritmi di ordinamento in linguaggio C Ordinamento per inserimento Insertion Sort con funzione ausiliaria int inserisci_valore(int vett[], int dim, int valore) { int i = dim; while (i > 0 && vett[i-1]

Подробнее

1.1 Concetti base dell Informatica: Algoritmi

1.1 Concetti base dell Informatica: Algoritmi 1.1 Concetti base dell Informatica: Algoritmi Insegnamento di Informatica Elisabetta Ronchieri Corso di Laurea di Economia, Università di Ferrara I semestre, anno 2014-2015 Elisabetta Ronchieri (Università)

Подробнее

INDICI PER FILE. Accesso secondario. Strutture ausiliarie di accesso

INDICI PER FILE. Accesso secondario. Strutture ausiliarie di accesso INDICI PER FILE Strutture ausiliarie di accesso 2 Accesso secondario Diamo per scontato che esista già un file con una certa organizzazione primaria con dati non ordinati, ordinati o organizzati secondo

Подробнее

Corso di Tecniche di Programmazione

Corso di Tecniche di Programmazione Corso di Tecniche di Programmazione Corsi di Laurea in Ingegneria Informatica ed Automatica Anno Accedemico 003/004 Proff. Giuseppe De Giacomo, Luca Iocchi, Domenico Lembo Dispensa : Algoritmi di Ordinamento

Подробнее

ALGORITMI Docente: Prof. Domenico Cantone

ALGORITMI Docente: Prof. Domenico Cantone CORSO SPECILE DI DURT NNULE PER IL CONSEGUIMENTO DELL BILITZIONE LL INSEGNMENTO NELL SCUOL SECONDRI DI I e II GRDO Indirizzo Fisico - Informatico - Matematico a.a. 00/07 - Classe - Informatica LGORITMI

Подробнее

ALGORITMI DI ORDINAMENTO ALGORITMI DI ORDINAMENTO

ALGORITMI DI ORDINAMENTO ALGORITMI DI ORDINAMENTO ALGORITMI DI ORDINAMENTO Scopo: ordinare una sequenza di elementi in base a una certa relazione d ordine lo scopo finale è ben definito algoritmi equivalenti diversi algoritmi possono avere efficienza

Подробнее

Algoritmi di ordinamento. Algoritmi. Selection sort semplificato - I. Selection sort semplificato - II

Algoritmi di ordinamento. Algoritmi. Selection sort semplificato - I. Selection sort semplificato - II Algoritmi Ver..4 Algoritmi di ordinamento Lo scopo è ordinare in senso [de]crescente il contenuto di un vettore di N elementi senza utilizzare un secondo vettore Esiste molta letteratura scientifica a

Подробнее

Un esempio di calcolo di complessità: insertion sort

Un esempio di calcolo di complessità: insertion sort Un esempio di calcolo di complessità: insertion sort Vediamo su un esempio come si può calcolare la complessità di un algoritmo... L esempio è un metodo semplice per ordinare arrays: insertion sort, o

Подробнее

Fondamenti di Informatica T-1 Modulo 2

Fondamenti di Informatica T-1 Modulo 2 Fondamenti di Informatica T-1 Modulo 2 1 Obiettivi di questa esercitazione 1. Array e funzioni 2. Array e funzioni ricorsive 3. Array e confronto di array 2 Esercizio 1 Creare un programma che legga da

Подробнее

Quicksort e qsort() Alessio Orlandi. 28 marzo 2010

Quicksort e qsort() Alessio Orlandi. 28 marzo 2010 Quicksort e qsort() Alessio Orlandi 28 marzo 2010 Intro Quicksort è l algoritmo di ordinamento più implementato, insieme con Mergesort. Tutte le librerie standard UNIX ne prevedono una implementazione.

Подробнее

Introduzione alla programmazione

Introduzione alla programmazione Introduzione alla programmazione Risolvere un problema Per risolvere un problema si procede innanzitutto all individuazione Delle informazioni, dei dati noti Dei risultati desiderati Il secondo passo consiste

Подробнее

Analisi algoritmi ricorsivi e relazioni di ricorrenza

Analisi algoritmi ricorsivi e relazioni di ricorrenza Analisi algoritmi ricorsivi e relazioni di ricorrenza Punto della situazione Finora abbiamo affrontato: il tempo di esecuzione di un algoritmo, l analisi asintotica con le notazioni asintotiche e la tecnica

Подробнее