Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                

Algoritmo Quicksort

Descargar como docx, pdf o txt
Descargar como docx, pdf o txt
Está en la página 1de 7

Descripcin del algoritmo

El algoritmo consta de los siguientes pasos:


Elegir un elemento de la lista de elementos a ordenar, al que llamaremos pivote. Resituar los dems elementos de la lista a cada lado del pivote, de manera que a un lado queden todos los menores que l, y al otro los mayores. Los elementos iguales al pivote pueden ser colocados tanto a su derecha como a su izquierda, dependiendo de la implementacin deseada. En este momento, el pivote ocupa exactamente el lugar que le corresponder en la lista ordenada. La lista queda separada en dos sublistas, una formada por los elementos a la izquierda del pivote, y otra por los elementos a su derecha. Repetir este proceso de forma recursiva para cada sublista mientras stas contengan ms de un elemento. Una vez terminado este proceso todos los elementos estarn ordenados.

Como se puede suponer, la eficiencia del algoritmo depende de la posicin en la que termine el pivote elegido.

En el mejor caso, el pivote termina en el centro de la lista, dividindola en dos sublistas de igual tamao. En este caso, el orden de complejidad del algoritmo es O(nlog n). En el peor caso, el pivote termina en un extremo de la lista. El orden de complejidad del algoritmo es entonces de O(n). El peor caso depender de la implementacin del algoritmo, aunque habitualmente ocurre en listas que se encuentran ordenadas, o casi ordenadas. Pero principalmente depende del pivote, si por ejemplo el algoritmo implementado toma como pivote siempre el primer elemento del array, y el array que le pasamos est ordenado, siempre va a generar a su izquierda un array vaco, lo que es ineficiente.

En el caso promedio, el orden es O(nlog n).

No es extrao, pues, que la mayora de optimizaciones que se aplican al algoritmo se centren en la eleccin del pivote.

[editar] Demostracin
Podramos probar el orden de ejecucin en el mejor caso de la siguiente manera: Vamos a suponer que el nmero total de elementos a ordenar es potencia de dos, es decir, n = 2k. de aqu podemos ver que k = log2(n), donde k es el nmero de divisiones que realizar el algoritmo.

En la primera fase del algoritmo habrn n comparaciones, en la segunda fase el algoritmo crear dos sublistas aproximadamente de tamao n/2. El nmero total de comparaciones de estas dos sublistas es: 2(n/2) = n. En la tercera fase el algoritmo procesar 4 sublistas ms, por tanto el nmero total de comparaciones en esta fase es 4(n/4) = n. En conclusin, el nmero total de comparaciones que hace el algoritmo es: n + n + n + ..... + n = kn, donde k = log2(n), por tanto el tiempo de ejecucin del algoritmo en el mejor caso es O(n.log2n)

Ejemplo
//Recibe un vector de enteros y el ndice del primer y ltimo elemento vlido del mismo void ordenarQuicksort(int[] vector, int primero, int ultimo){ int i=primero, j=ultimo; int pivote=vector[(primero + ultimo) / 2]; int auxiliar; do{ while(vector[i]<pivote) i++; while(vector[j]>pivote) j--; if (i<=j){ auxiliar=vector[j]; vector[j]=vector[i]; vector[i]=auxiliar; i++; j--; } } while (i<=j); if(primero<j) ordenarQuicksort(vector,primero, j); if(ultimo>i) ordenarQuicksort(vector,i, ultimo); }

En el siguiente ejemplo se marcan el pivote y los ndices i y j con las letras p, i y j respectivamente. Comenzamos con la lista completa. El elemento pivote ser el 4:
5 - 3 - 7 - 6 - 2 - 1 - 4 p

Comparamos con el 5 por la izquierda y el 1 por la derecha.

5 - 3 - 7 - 6 - 2 - 1 - 4 i j p

5 es mayor que 4 y 1 es menor. Intercambiamos:


1 - 3 - 7 - 6 - 2 - 5 - 4 i j p

Avanzamos por la izquierda y la derecha:


1 - 3 - 7 - 6 - 2 - 5 - 4 i j p

3 es menor que 4: avanzamos por la izquierda. 2 es menor que 4: nos mantenemos ah.
1 - 3 - 7 - 6 - 2 - 5 - 4 i j p

7 es mayor que 4 y 2 es menor: intercambiamos.


1 - 3 - 2 - 6 - 7 - 5 - 4 i j p

Avanzamos por ambos lados:


1 - 3 - 2 - 6 - 7 - 5 - 4 iyj p

En este momento termina el ciclo principal, porque los ndices se cruzaron. Ahora intercambiamos lista[i] con lista[sup] (pasos 16-18):
1 - 3 - 2 - 4 - 7 - 5 - 6 p

Aplicamos recursivamente a la sublista de la izquierda (ndices 0 - 2). Tenemos lo siguiente:


1 - 3 - 2

1 es menor que 2: avanzamos por la izquierda. 3 es mayor: avanzamos por la derecha. Como se intercambiaron los ndices termina el ciclo. Se intercambia lista[i] con lista[sup]:
1 - 2 - 3

El mismo procedimiento se aplicar a la otra sublista. Al finalizar y unir todas las sublistas queda la lista inicial ordenada en forma ascendente.
1 - 2 - 3 - 4 - 5 - 6 - 7

Algoritmo de Ordenamiento Quicksort.


Sea x un arreglo y n el nmero de elementos en arreglo que se debe ordenar. Elegir un elemento a de una posicin especifica en el arreglo (por ejemplo, a puede elegirse como el primer elemento del arreglo. Suponer que los elemento de x estn separados de manera que a est colocado en la posicin j y se cumplen las siguientes condiciones.
1.- Cada uno de los elementos en las posiciones de 0 a j-1 es menor o igual que a. 2.- Cada uno de los elementos en las posiciones j+1 a n-1 es mayor o igual que a.

Observe que si se cumplen esas dos condiciones para una a y j particulares, a es el j-simo menor elemento de x, de manera que a se mantiene en su posicin j cuando el arreglo est ordenado en su totalidad. Si se repite este procedimiento con los subarreglos que van de x[0] a x[j-1] y de x[j+1] a x[n-1] y con todos los subarreglos creados mediante este proceso, el resultado final ser un archivo ordenado.

Ilustremos el quicksort con un ejemplo. Si un arreglo esta dado por:

x = [25 57 48 37 12 92 86 33]

y el primer elemento se coloca en su posicin correcta, el arreglo resultante es:

x = [12 25 57 48 37 92 86 33]

En este punto 25 esta en su posicin correcta por lo cual podemos dividir el arreglo en

x = [12] 25 [57 48 37 92 86 33]

Ahora repetimos el procedimiento con los dos subarreglos

x = 12 25 [48 37 33] 57 [92 86]

x = 12 25 33 [37 48] 57 [86] [92]

x = 12 25 33 [37 48] 57 86 92

x = 12 25 33 37 48 57 86 92

El procedimiento es entonces.

Buscar la particin del arreglo j. Ordenar el subarreglo x[0] a x[j-1] Ordenar el subarreglo x[j+1] a x[n-1]

Su implementacin en Java es:

public void quiksort(int x[],int lo,int ho) { int t, l=lo, h=ho, mid;

if(ho>lo)

{ mid=x[(lo+ho)/2]; while(l<h) { while((l<ho)&&(x[l]<mid)) while((h>lo)&&(x[h]>mid)) if(l<=h) { t = x[l]; ++l; --h;

x[l] = x[h]; x[h] = t; ++l; --h; } }

if(lo<h) quiksort(x,lo,h); if(l<ho) quiksort(x,l,ho); } }


Mejor Caso Peor Caso Caso Promedio Estabilidad Memoria Adicional Comparacin

QuickSort

No Estable

No

Compara

QuickSort : - Este Algoritmo es inestable ya que si se pueden producir intercambios de claves con datos iguales, es posible que se altere el orden relativo inicial del arreglo a ser ordenado. - Este Algoritmo no requiere memoria adicional, ya que los subarreglos son ordenados In Situ.

-Tambin apreciamos que funciona en base a comparaciones en los WHILEs dentro de PARTITION, ah compara varias veces. - El caso promedio La complejidad para dividir una lista de n es O(n). De cada sublista se crean en promedio dos sublistas ms de largo n/2. Por lo tanto la complejidad se define en forma recurrente como: f(1) = 1 f(2) = 2 + 2*f(1) .. As llegamos a la recursividad: f(n) = n + 2*f(n/2)

Y esto significa una complejidad de O( ). - El Peor Caso de este Algoritmo es cuando la lista est ordenada (curiosamente) porque en cada llamada recursiva el arreglo es dividido en una parte que contiene todos los elementos del arreglo menos el pivote (que vendra siendo el mayor o el menor de la lista) y otra vaca. En este caso la complejidad del algoritmo es O( ).

- En el mejor caso el pivote es siempre la media de todos los elementos, de esta forma el arreglo se divide en dos partes equilibradas siendo la complejidad del algoritmo O( ).

También podría gustarte