Sunteți pe pagina 1din 31

Limbaje de programare I

CURS 11
ALGORITMI DE CĂUTARE ȘI SORTARE

Limbaje de programare 1 1
ALGORITMI DE CĂUTARE
• Algoritm de căutare – metodă pentru găsirea unui
articol sau grup de articole cu anumite proprietăți în
cadrul unei colecții de articole
• Colecția poate fi implicită
– exemplu – găsirea rădăcinii pătrate ca o problemă de
căutare
• Enumerare exhaustivă
• Căutare binară
• Newton-Raphson (în detaliu)
• Colecția poate fi explicită
– exemplu – se află înregistrarea student într-o colecție de
date stocată?

Limbaje de programare 1 2
ALGORITMI DE CĂUTARE
• Căutare liniară
– Metoda forței brute
– Lista nu trebuie să fie sortată
• Căutare binară
– Lista TREBUIE să fie sortată pentru a se obține
rezultatul corect
– Vom vedea două implementări diferite ale
algoritmului

Limbaje de programare 1 3
Căutare liniară în lista nesortată

• Trebuie trecut prin toate elementele pentru a


decide că ceea ce căutăm nu e în listă
• O(len(L)) pentru buclă * O(1) pentru a testa dacă
e == L[i]
• Complexitatea este O(n) – unde n este len(L)
Limbaje de programare 1 4
Căutare liniară în lista sortată

• Trebuie căutat numai până se ajunge la un


element mai mare decât cel căutat
• O(len(L)) pentru buclă * O(1) pentru a testa dacă
e == L[i]
• Complexitatea este O(n) – unde n este len(L)
Limbaje de programare 1 5
Căutare binară
1. Alege un index i, care împarte lista în jumătate
2. Verifică dacă L[i] == e
3. Dacă nu, verifică dacă L[i] este mai mare sau mai mic decât
e
4. În funcție de răspuns, se caută după e în jumătatea stângă
sau dreaptă a lui L
• O versiune nouă a algoritmului Divide et Impera (Divide &
Conquer)
• Împarte în versiuni mai mici ale problemei (liste mai mici),
plus câteva operații simple
• Răspunsul de la versiunea mai mică este răspunsul la
problema originală

Limbaje de programare 1 6
Complexitatea problemei
• Oprește căutarea
în listă când
1 = n/2i
deci
i = log n
• Complexitatea
este
O(log n) – unde n
este len(L)

Limbaje de programare 1 7
Căutare binară – implementare 1

Limbaje de programare 1 8
Căutare binară – implementare 2

Limbaje de programare 1 9
Complexitatea celor 2 implementări
• Implementare 1
– O(log n) apelul căutare binară
– O(n) pentru fiecare apel al căutării binare pentru a
copia lista
– → O(n log n)
– → O(n) pentru o mărginire exactă pentru că lungimea
listei este înjumătățită la fiecare apel recursiv
• Implementare 2
– Trimite lista și indecșii, ca parametrii
– Lista nu este copiată, doar retrimisă
– → O(log n)

Limbaje de programare 1 10
Căutare în lista sortată
• Folosind căutare liniară, căutarea unui element
este O(n)
• Folosind căutarea binară, se poate căuta un
element în O(log n)
– Presupunem lista sortată!
• Când este mai bine să sortăm înainte de a căuta?
– SORT + O(log n) < O(n) → SORT < O(n) – O(log n)
– Când sortare este < O(n) → niciodată!

Limbaje de programare 1 11
Amortizarea costurilor
• De ce să sortăm mai întâi?
• În unele cazuri, putem sorta o listă o dată și
apoi să facem mai multe căutări
• Amortizarea costului sortării pe durata mai
multor căutări
• SORT + K*O(log n) < K*O(n)
• pentru K mare, timpul pentru SORT devine
irelevant
Limbaje de programare 1 12
MONKEY SORT
• Poreclit și: bogosort, stupid sort, slowsort,
permutation sort, shotgun sort
• Pentru a sorta un pachet de cărți de joc:
– Le aruncăm în aer
– Le strângem
– Sunt sortate?
– Repetă dacă nu

Limbaje de programare 1 13
Complexitatea

• Cel mai bun caz: O(n) unde n = len(L) pentru a


verifica dacă L este sortată
• Cel mai rău caz: O(?) este nelimitat dacă
suntem foarte ghinioniști
Limbaje de programare 1 14
Bubble sort
• Compară perechi consecutive de elemente
• Interschimbă elementele în perechi a.î. primul să
fie mai mic
• Când se ajunge la sfârșitul listei, se reîncepe
• Se oprește când nu s-a mai făcut nicio
interschimbare

https://commons.wikimedia.org/wiki/File:Bubble_s
ort_animation.gif

Limbaje de programare 1 15
Complexitatea

• Bucla for internă este pentru comparații


• Bucla while externă este pentru realizarea trecerilor
multiple până când nu se mai fac interschimbări
• O(n2) unde n = len(L) pentru a face len(L)-1 comparații
și len(L)-1 treceri
Limbaje de programare 1 16
Selection sort
• Primul pas
– Extrage elementul minim
– Interschimbă-l cu elementul de la indexul 0
• Pasul următor
– În sub-lista rămasă, extrage elementul minim
– Interschimbă-l cu elementul de la indexul 1
• Menține partea stângă a listei sortată
– La pasul i, primele i elemente din listă sunt sortate
– Toate celelalte elemente sunt mai mari decât primele i elemente

https://commons.wikimedia.org/wiki/File:Selection_Sort_Ani
mation.gif

Limbaje de programare 1 17
Complexitatea

• Bucla exterioară se execută de len(L) ori


• Bucla interioară se execută de len(L) – i ori
• Complexitatea este O(n2) unde n = len(L)

Limbaje de programare 1 18
MERGE SORT
• Utilizează abordarea divide et impera
1. Dacă lista este de lungime 0 sau 1, este sortată
2. Dacă lista are mai mult de un element, se
împarte în două liste și se sortează fiecare
3. Unește sublistele sortate
1. Se compară primul element din fiecare, se pun cel
mai mic la sfârșitul rezultatului
2. Când una din liste de goală, se copiază restul
celeilalte liste

Limbaje de programare 1 19
MERGE SORT

Limbaje de programare 1 20
MERGE SORT

Limbaje de programare 1 21
MERGE SORT

Limbaje de programare 1 22
MERGE SORT

Limbaje de programare 1 23
MERGE SORT

https://commons.wikimedia.org/wiki/File:Merge_sort_animation.gif

Limbaje de programare 1 24
Exemplu

Limbaje de programare 1 25
Pasul de unire a sublistelor

Limbaje de programare 1 26
Complexitatea pasului de unire a
sublistelor
• Parcurge două liste, numai una este trecută
• Compară doar cele mai mici elemente din
fiecare sublistă
• O(len(left) + len(right)) elemente copiate
• O(len(longer list)) comparații
• Liniară după lungimile listelor

Limbaje de programare 1 27
MERGE SORT – algoritm recursiv

Limbaje de programare 1 28
Limbaje de programare 1 29
Complexitatea
• La primul nivel de recursivitate
– n/2 elemente în fiecare listă
– O(n) + O(n) = O(n) unde n = len(L)
• La al doilea nivel de recursivitate
– n/4 elemente în fiecare listă
– Două reuniri → O(n)
• Fiecare nivel de recursivitate este O(n)
• Împărțirea listei în două cu fiecare apel recursiv
– O(log(n))
• Complexitatea este O(n log(n))

Limbaje de programare 1 30
Rezumat sortare
• bogo sort
– aleatoriu, O() nemărginit
• bubble sort
– O(n2)
• selection sort
– O(n2)
– Primele i elemente sunt întotdeauna sortate
• merge sort
– O(n log(n))
• O(n log(n)) este cel mai rapid sort care se poate face

Limbaje de programare 1 31

S-ar putea să vă placă și