Professional Documents
Culture Documents
O problema da separao
222
111
777
999
444
555
666
666
222
111
777
555
444
555
777
555
888
999
888
Exerccios 1
25. while(v[i]<v[q])++i;
26. while(v[j]>v[q])j;
27. if(i<=j){
28. t=v[i],v[i]=v[j],v[j]=t;
29. ++i,j;}
30. }while(i<=j);
31. returni;}
O algoritmo da separao
Eis como D. Gries implementa o algoritmo da
separao. A funo rearranja o vetor v[p..r] e
devolve um elemento j do conjunto p..rtal que v[p..j
1]?v[j]<v[j+1..r]:
intsepara(intv[],intp,intr)
{
intc=v[p],i=p+1,j=r,t;//1
while(1){//2
while(i<=r&&v[i]<=c)++i;//3
while(c<v[j])j;//4
if(i>=j)break;//5
t=v[i],v[i]=v[j],v[j]=t;//6
++i;j;//7
}//8
v[p]=v[j],v[j]=c;//9
returnj;//10
}
?c ?c ?c ?c
//oselementosdovetoredevolvejemp..r
//talquev[p..j1]<=v[j]<v[j+1..r].
staticint
separa(intv[],intp,intr)
intc=v[p],i=p+1,j=r,t;
while(/*A*/i<=j){
if(v[i]<=c)++i;
elseif(c<v[j])j;
else{
t=v[i],v[i]=v[j],v[j]=t;
++i;j;
//agorai==j+1
v[p]=v[j],v[j]=c;
returnj;
?c ?c ?c
>c >c
i=j
?c ?c ?c ?c
i==j+1,
p?j?r,
v[p+1..j]?c e v[j+1..r]>c.
Assim, v[p..j1]?v[j]<v[j+1..r] na fim da
execuo da funo, como prometido.
(Observe que a varivel i serve de sentinela para j e
vice-versa. Isso torna desnecessrias as comparaes
de i com r toda vez que i incrementado e torna
desnecessrias as comparaes de j com p toda vez
que j decrementado. Esse detalhe contribui para
tornar a funo particularmente rpida.)
Exerccios 2
1. Mostre o resultado da operao separa(v,0,15), sendo v[0..15] o
vetor
2. 33225533442299665511887733886666
36. v[j]=c;
37. returnj;}
Quicksort bsico
Agora que resolvemos o problema da separao,
podemos cuidar do Quicksort propriamente dito. O
algoritmo usa a estratgia dadiviso e conquista e tem
a aparncia de um Mergesort ao contrrio:
//Estafunorearranjaqualquervetor
//v[p..r]emordemcrescente.
void
quicksort(intv[],intp,intr)
intj;//1
if(p<r){//2
j=separa(v,p,r);//3
quicksort(v,p,j1);//4
quicksort(v,j+1,r);//5
quicksrt(v,p,j1);
p=j+1;
}
}
Exerccios 3
1. Que acontece se trocarmos p<r por p!=r na linha 2 do quicksort?
Que acontece se trocarmos j1 por j na linha 4 do cdigo? Que
acontece se trocarmos j+1 por j na linha 5?
2. PEGADINHA. Quais so os invariantes da funo quicksort?
3. Submeta o vetor 77553399 indexado por 1..4
funo quicksort. Teremos a seguinte sequncia de chamadas da
funo:
4. quicksort(v,1,4)
5. quicksort(v,1,2)
6. quicksort(v,1,0)
7. quicksort(v,2,2)
8. quicksort(v,4,4)
Animaes do Quicksort
Animao do Quicksort, de Mike Bostock (veja
tambm uma visualizao esttica, uma variante,
e uma outra forma de visualizao)
Sorting Algorithms Animation, de David R. Martin
Demonstrao animada do Quicksort, copiada do
stio de R. Sedgewick (Universidade de Princeton)
Animao de algoritmos de ordenao, de Nicholas
Andr Pinho de Oliveira
Quick-sort com dana folclrica hngara,
Universidade Sapientia (Romnia)
Exerccios 4
1. CRONOMETRAGEM. Escreva um programa que cronometre sua
implementao do Quicksort (use a funo clock da biblioteca time).
Divida os tempos por n logn para comparar com as previses
tericas.
2. VERSO TRUNCADA. Escreva uma verso do algoritmo Quicksort
com cutof para vetores pequenos: quando o vetor a ser ordenado
tiver menos que M elementos, a ordenao passa a ser feita
pelo algoritmo de insero. O valor de M pode ficar entre 10
e 20. (Esse truque usado na prtica porque o algoritmo de
insero mais rpido que o Quicksort puro quando o vetor
pequeno. O fenmeno muito comum: algoritmos sofisticados so
tipicamente mais lentos que algoritmos simplrios quando o volume
de dados pequeno.)
3. [Pedro Rey] A seguinte funo promete rearranjar o vetor v[p..r] em
ordem crescente. Mostre que a funo est correta. Estime o
consumo de tempo da funo.
4. voidpsort(intv[],intp,intr){
5. if(p>=r)return;
6. if(v[p]>v[r]){
7. intt;
8. t=v[p],v[p]=v[r],v[r]=t;}
9. psort(v,p,r1);
10. psort(v,p+1,r);}
//emordemcrescente.
void
quickSort(intv[],intp,intr)
intj;
while(p<r){
j=separa(v,p,r);
if(jp<rj){
quickSort(v,p,j1);
p=j+1;
}else{
quickSort(v,j+1,r);
r=j1;
Exerccios 5
1. Suponha que a seguinte funo aplicada a um vetor
com n elementos. Mostre que a altura da pilha de execuo pode
passar de por log n.
2. voidquicks(intv[],intp,intr){
3. intj;
4. if(p<r){
5. j=separa(v,p,r);
6. if(jp<rj){
7. quicks(v,p,j1);
8. quicks(v,j+1,r);}
9. else{
10. quicks(v,j+1,r);
11. quicks(v,p,j1);}}}
12. if(v[j]>v[k]{
13. t=v[j],v[j]=v[k],v[k]=t;
14. ff=ff;
15. }
16. if(ff==1)k;
17. else++j;
18. }
19. quick_FlipFlop(v,p,j1);
20. quick_FlipFlop(v,j+1,r);
21. }
22. }
23.
A verso seguinte (veja livro de Cormen,
Leiserson e Rivest) usa a primeira das duas
formulaes do problema da separao
mencionadas acima: rearranja v[p..r] de modo
que v[p..j]?v[j+1..r] para algum j em p..r1.
24. //Afunorearranjaovetorv[p..r]
25. //emordemcrescente.
26.
27. voidquick_CLR(intv[],intp,intr)
28. {
29. intc,i,j,t;
30. if(p<r){
31. c=v[p];
32. i=p1,j=r+1;
33. while(1){
34. doj;while(v[j]>c);
35. do++i;while(v[i]<c);
36. if(i>=j)break;
37. t=v[i],v[i]=v[j],v[j]=t;
38. }
39. quick_CLR(v,p,j);
40. quick_CLR(v,j+1,r);
41. }
42. }
43.
Eis outra verso (se no me engano, ela est
no livro de Sedgewick). Exerccio: formule com
preciso o problema da separao que essa verso
resolve.
44. //Afunorearranjaovetorv[p..r]
45. //emordemcrescente.
46.
47. voidquick_S(intv[],intp,intr){
48. intc,i,j,t;
49. if(p<r){
50. c=v[(p+r)/2];
51. i=p,j=r;
52. while(i<=j){
53. while(v[i]<c)++i;
54. while(c<v[j])j;
55. if(i<=j){
56. t=v[i],v[i]=v[j],v[j]=t;
57. ++i,j;
58. }
59. }
60. quick_S(v,p,j);
61. quick_S(v,i,r);
62. }
63. }
64.
A seguinte verso do Quicksort sugerida
no livro de Sedgewick. Exerccio: formule com
preciso o problema da separao que essa verso
resolve.
65. #definetroca(A,B){intt=A;A=B;B=t;}
66. voidquick_S2(intv[],intp,intr){
67. if(p<r){
68. inti=p1,j=r,c=v[r];
69. while(1){
70. while(v[++i]<c);
71. while(c<v[j])if(j==p)break;
72. if(i>j)break;
73. troca(v[i],v[j]);
74. }
75. troca(v[i],v[r]);
76. quick_S2(v,p,j);
77. quick_S2(v,i+1,r);
78. }
79. }
44
55
77
95
99
22
25
41
66
88
89
bc1435 Mediana
Publicado em 28/05/2013
inteiros descobrir o
elemento da posio
mediana?
Vamos enunciar o problema de um modo mais genrico:
Problema da Seleo
inteiro
de
inteiros (distintos) e um
Resposta: O elemento
outros elementos de
Dadoumvetor
denmerosinteiros,com
Devolve
eoselementosde
rearranjadosdemodoque
se
se
seno
DadoumvetorA[1..n]denmerosinteiroseuminteirokentre1en
DevolveoksimomenorelementodeA.
1Se(n=1)devolva(A[1])
2Seno{
3d<Partio(A[1..n])
4Se(k<d)
5devolvaSeleoPartio(A[1..d1],k)
6SenoSe(k>d)
7devolvaSeleoPartio(A[d+1..n],kd)
8Senodevolva(A[p])}
no
, portanto
ento
, portanto
e tomando
da ordem de
vezes
temos
, portanto
Um modo de escolher o piv que podemos adotar como a que foi feita
no quicksortprobabilstico:
escolhemos
um
elemento
do
vetor
aleatoriamente para ser o piv. Tal piv bom se no for dos 10%
menores elementos do vetor nem dos 10% maiores elementos do vetor.
A probabilidade de sortear um piv bom
e o nmero esperado
mximo
logo
Seleo_probabilstico
Seleo_probabilstico(A[1..n],k)
DadosumvetordeinteirosA[1..n]uminteirokentre1en.
DeterminaoksimomenorelementodeA.
1Se(n=1)devolva(A[1])
2Seno{
3sorteierem[1..n];A[r]<>A[i]
4p<Partio(A[1..n])
5Se(k<=p)
6devolva(Seleo_probabilstico(A[1..p],k))
7Seno
8devolva(Seleo_probabilstico(A[p+1..n],pk))}
1.Dividaosnelementosdaentradaem
gruposdecinco
elementoscada(enomximoumgrupoconsistindodoselementos
restantes);
2.Descubraamedianaemcadaumdos
grupos;
3.UseSELEOrecursivamenteparadescobriramedianaA[mdm]das
medianas;
4.ParticioneaentradausandoA[mdm]comopiv;
5.Sek<=mdmuseSELEOrecursivamenteemA[1..mdm]paraacharok
simomenor;
6.SenouseSELEOrecursivamenteemA[mdm..n]paraacharo(kmdm)
simomenor.
Detalhamento:
Seleo
Seleo(A[1..n],k)
DadoumvetorA[1..n]einteiroseuminteirokentre1en
DevolveoksimomenorelementodeA
1.Se(n<=25)useforabruta;
2.Seno{
3.m<
n/5
4.Paraide1atm
B[i]<Seleoforabruta(A[5i4..5i],3)
6.mdm<Seleo(B[1..m],
m/2
)
7.A[1]<>A[mdm]
8.d<Partio(A[1..n])
9.Se(k<d)Devolva(Seleo(A[1..d1],k))
10.SenoSe(k>d)Devolva(Seleo(A[d+1..n],kd))
10.SenoDevolva(A[mdm])}.
Simetricamente,
elementos
o total de no mximo
comparaes portanto,
cuja soluo
Mximo e mnimo
Determinar o mnimo de um sequncia
mais
fcil
exatamente
que
de
inteiros
Seleo(A[1..n],1),
pode
ser
feito
usando
comparaes:examinar cada elemento do conjunto,
comparaes.
de
nmeros inteiros?
nmeros,
comparaes.
nmeros.
elementos pode