Este documento introduce el tema del ordenamiento de datos, el cual es una parte importante en ciencias de la computación. Se mencionan algunos algoritmos de ordenamiento eficientes que alcanzan el límite inferior de complejidad nlgn. Luego, se presenta un nuevo enfoque de ordenamiento donde la única operación disponible es intercambiar dos términos adyacentes, lo cual siempre permite ordenar un conjunto de números de esta manera. Finalmente, se plantea un problema relacionado a este enfoque.
4. Ordenamiento
• El ordenamiento de los datos consiste en disponer
un conjunto de datos (o una estructura) en algún
determinado orden con respecto a alguno de sus
campos.
▫ Clave: Campo por el cual se ordena.
• Según donde estén almacenados los datos a
ordenar, podemos decir que el ordenamiento es:
▫ Interna: Arrays, listas o árbol. Típicamente en RAM.
▫ Externa: En Archivos en discos.
5. Orden
• Una lista de datos está ordenada por la clave k si la lista
está en orden con respecto a la clave anterior.
• Este Orden puede ser:
▫ Ascendente: (i<j) entonces (k[i]<=k[j])
▫ Descendente: (i>j) entonces (k[i]>=k[j])
• Hay Numerosos Métodos de Ordenamiento que difieren
en eficiencia.
▫ Análisis de algoritmo orientado a las comparaciones
realizadas por cada uno.
▫ Las comparaciones serán función de “n”. Siendo “n” el
tamaño del vector a Ordenar.
6. Clasificación de Métodos de Ordenamiento
• Analizaremos los siguientes métodos:
▫ Básicos: Son eficaces en Listas pequeñas
Burbuja e Intercambio: simple pero Ineficiente.
Selección e inserción: Recomendados.
▫ Avanzados: Son eficaces en Listas grandes.
Merge Sort: muy extendido
Quick Sort: muy extendido
Shell Sort: muy extendido
Counting Sort: el mas rápido para números
8. Ordenamiento por Intercambio
(Conocido como Burbuja)
• El más sencillo de todos. Se basa en:
▫ La lectura sucesiva de la lista a ordenar,
▫ Comparando el elemento inferior de la lista con todos
los restantes
▫ Efectuando el Intercambio de posiciones cuando el
orden resultante no sea correcto.
• Siendo n la cantidad de elementos, Realizará al
menos n–1 pasadas.
9. Ejemplo - Ordenamiento por Intercambio
Pasada 1: Se compara a[1] con todos, así primero se cambia a[1] con a[2] pues a[1] >
a[2] y debe ser Ascendente, es decir a[1]<a[2] …y por utimo a[1] con a[4]
a[1] a[2] a[3] a[4] a[1] a[2] a[3] a[4] a[1] a[2] a[3] a[4]
8 4 6 2 4 8 6 2 2 8 6 4
Pasada 2: El elemento mas pequeño esta en a[1] y se analiza la sublista restante.
Al cabo de la pasada, el segundo mas chico esta en a[2]….
Pasada 3:
a[1] a[2] a[3] a[4] a[1] a[2] a[3] a[4]
2 4 8 6 2 4 6 8
Pasada i: Al cabo de la pasada i, el elemento de orden i, está en a[i]
10. Algoritmo: Ordenamiento por Intercambio
Algoritmo ordIntercambio (a[], n)
i, k, aux: enteros /* se realizan n-1 pasadas */
para i desde 1 hasta n-1 hacer
para k desde i+1 hasta n hacer
si a[i] > a[k] entonces
aux a[i] Complejidad (n)(n–1)
a[i] a[k]; Del Orden F(n)=n2.
a[k] aux ; Mejor Caso = O(n ) 2
Peor Caso = O(n2)
11. Código en C++
Ordenamiento por Intercambio
void ordIntercambio (int a[], int n)
{
for (int i=0; i < n-1; i++)
{
for (int k=i+1; k<n; k++)
{
if (a[i] > a[k])
{
int aux = a[i];
a[i] = a[k];
a[k] = aux;
}
}
}
}
13. Burbuja (Verdadera Burbuja)
• Los elementos burbujean:
▫ Los mas grandes, caen al fondo del arreglo (posición n)
▫ Los mas chicos suben a la cima (posición 1).
• Estudia parejas de elementos Adyacentes
▫ a[1] y a[2], a[2] y a[3]…a[i] y a[i+1]… a[n–1] y a[n].
▫ Si a[i+1] < a[i] Entonces Los INTERCAMBIA
• Algoritmo:
▫ Pasada 1: considera desde (a[1], a[2]) hasta (a[n–1], a[n]).
En a[n] esta el elemento mas grande.
▫ Pasada 2: considera desde (a[1], a[2]) hasta (a[n–2], a[n–1]).
En a[n–1] esta el segundo elemento mas grande.
▫ Pasada i: considera desde (a[1], a[2]) hasta (a[n–i], a[n-i+1]).
En a[n–i+1] esta el elemento de orden i.
▫ El proceso termina con la pasada n–1
El elemento mas pequeño esta en a[1].
15. Algoritmo: Ordenamiento por Burbuja
Algoritmo ordBurbuja (a[], n)
i, k, aux: enteros
Repetir con i desde 1 hasta n-1
Repetir con k desde 1 hasta n-i
si (a[k] > a[k+1]) entonces
aux = a[k]
a[k] = a[k+1]
a[k+1] = aux
Mejor Caso = O(n2)
Caso Prom. = O(n2)
Peor Caso = O(n2)
16. Algoritmo: Ordenamiento por Burbuja
(Modificado)
Algoritmo ordBurbujaModificado (a[], n)
i, k, aux: enteros
ordenado: boolean
Repetir con i desde 1 hasta n-1
ordenado = true
Repetir con k desde 1 hasta n-i
si (a[k] > a[k+1]) entonces
aux = a[k]
a[k] = a[k+1]
a[k+1] = aux
ordenado = false
si (ordenado) break Mejor Caso = O(n)
Caso Prom. = O(n2)
Peor Caso = O(n2)
17. Código en C++:
Ordenamiento por Burbuja (Modificado)
void ordBurbujaModificado (int a[], int n)
{
bool ordenado;
for (int i=0; i < n-1; i++)
{
ordenado = true;
for (int j=0; j < n - (i + 1); j++)
{
if (a[j] > a[j+1])
{
int aux = a[j];
a[j] = a[j+1];
a[j+1] = aux;
ordenado = false;
}
}
if (ordenado) break;
}
}
19. Ordenamiento Por Selección
• Realiza sucesivas pasadas que
▫ Buscan el elemento más pequeño de la lista a y lo
escribe al frente de la lista a[1].
▫ Considera las posiciones restantes, a[2]…a[n]
▫ Finaliza cuando ya no hay Posiciones Restantes.
• En la pasada i
▫ Está Ordenado: desde a[1] hasta a[i–1].
▫ Está Desordenado: Desde a[i] hasta a[n].
• El proceso continua n–1 vueltas.
20. Ejemplo: Ordenamiento por Selección
a[1] a[2] a[3] a[4]
Lista Original:
51 21 39 80
Pasada 1: Lista entre 1 y 4. Selecciona el menor (21) a[1] a[2] a[3] a[4]
y lo pasa al a[1]
21 51 39 80
Pasada 2: Lista entre 2 y 4. Selecciona el menor (39) a[1] a[2] a[3] a[4]
y lo pasa al a[2] 21 39 51 80
a[1] a[2] a[3] a[4]
Pasada 3: Lista entre 3 y 4. No selecciona nada.
21 39 51 80
21. Algoritmo: Ordenamiento por Selección
Algortimo ordSeleccion (a[], n)
menor, k, j: enteros;
Repetir con i desde 1 hasta n-1
k=i /* comienzo de la exploración en índice i */
menor = a[i]
Repetir con j desde i+1 hasta n
si a[j] < menor entonces
menor = a[j]
k=j Complejidad (n (n–1))/2
a[k] = a[i] Del Orden F(n)=n2.
a[i] = menor Mejor Caso = O(n ) 2
Caso Prom. = O(n2)
Peor Caso = O(n2)
22. Código en C++:
Ordenamiento por Selección
void ordSeleccion (int a[], int n)
{
int k, menor;
for (int i=0; i < n-1; i++)
{
k = i;
menor = a[i];
for (int j=i+1; j<n; j++)
{
if (a[j] < menor)
{
menor = a[j];
k = j;
}
}
a[k] = a[i];
a[i] = menor;
}
}
24. Ordenamiento Por Inserción
• Similar al proceso de ordenar tarjetas en un tarjetero por orden
alfabético:
▫ Consiste en insertar un elemento en su posición correcta, dentro de
una lista que ya está Ordenada.
• Algoritmo:
▫ El 1er elemento a[1] se lo considera ordenado.
▫ Se inserta a[2] en la posición correcta, delante o detrás del a[1], según
sea mayor o menor.
▫ Por cada bucle i (desde i = 2 hasta n) se explora la sublista a[1]..a[i–1]
buscando la posición correcta de inserción del elemento a[i].
▫ Al dejar vacía la posición a[i] se impone un desplazamiento de todo el
vector, desde el lugar de inserción.
25. Ejemplo: Ordenamiento por Inserción
a[1] a[2] a[3] a[4]
Lista Original:
51 21 10 15
Pasada 1: Comenzamos en a[2] desplazando a la a[1] a[2] a[3] a[4]
derecha todos los valores que sean mayores a 21 (a[1])
21 51 10 15
Pasada 2: El 10 lo mueve hasta a[1] a[1] a[2] a[3] a[4]
10 21 51 15
a[1] a[2] a[3] a[4]
Pasada 3: El 15 lo mueve hasta a[2].
10 15 21 51
26. Algoritmo: Ordenamiento por Inserción
Algoritmo ordInsercion (a[], n)
i, j, aux : enteros
Repetir con i desde 2 hasta n
aux = a[i]
k = i-1
Repetir mientras (k >= 1) y (aux < a[k])
a[k+1] = a[k]
Complejidad (n (n–1))/2
k = k-1 Del Orden F(n)=n2.
a[k+1] = aux Mejor Caso = O(n)
Caso Prom. = O(n+d)
Peor Caso = O(n2)
d es la cantidad de inversiones
27. Código en C++:
Ordenamiento por Inserción
void ordInsercion (int a[], int n)
{
int aux, k;
for (int i=1; i<n; i++)
{
aux = a[i];
k = i-1;
while (k >= 0 && aux < a[k])
{
a[k+1] = a[k];
k--;
}
a[k+1] = aux;
}
}
29. Ejercicio 1 - UVA - 10327
Sorting in computer science is an important part. Almost every problem can be solved effeciently if sorted
data are found. There are some excellent sorting algorithm which has already acheived the lower bound
nlgn. In this problem we will also discuss about a new sorting approach. In this approach only one
operation ( Flip ) is available and that is you can exchange two adjacent terms. If you think a while, you
will see that it is always possible to sort a set of numbers in this way.
The Problem
A set of integers will be given. Now using the above approach we want to sort the numbers in ascending
order. You have to find out the minimum number of flips required. Such as to sort "1 2 3" we need no flip
operation whether to sort "2 3 1" we need at least 2 flip operations.
The Input
The input will start with a positive integer N ( N<=1000 ). In next few lines there will be N integers. Input
will be terminated by EOF.
The Output
For each data set print "Minimum exchange operations : M" where M is the minimum flip operations
required to perform sorting. Use a seperate line for each case.
Sample Input
3
1 2 3
3
2 3 1
Sample Output
Minimum exchange operations : 0
Minimum exchange operations : 2
30. Ejercicio 2 - UVA - 299
At an old railway station, you may still encounter one of the last remaining ``train swappers''. A train swapper is an employee of the railroad,
whose sole job it is to rearrange the carriages of trains.
Once the carriages are arranged in the optimal order, all the train driver has to do, is drop the carriages off, one by one, at the stations for which
the load is meant.
The title ``train swapper'' stems from the first person who performed this task, at a station close to a railway bridge. Instead of opening up
vertically, the bridge rotated around a pillar in the center of the river. After rotating the bridge 90 degrees, boats could pass left or right.
The first train swapper had discovered that the bridge could be operated with at most two carriages on it. By rotating the bridge 180 degrees,
the carriages switched place, allowing him to rearrange the carriages (as a side effect, the carriages then faced the opposite direction, but train
carriages can move either way, so who cares).
Now that almost all train swappers have died out, the railway company would like to automate their operation. Part of the program to be
developed, is a routine which decides for a given train the least number of swaps of two adjacent carriages necessary to order the train. Your
assignment is to create that routine.
Input Specification
The input contains on the first line the number of test cases (N). Each test case consists of two input lines. The first line of a test case contains an
integer L, determining the length of the train ( ). The second line of a test case contains a permutation of the numbers 1 through L, indicating the
current order of the carriages. The carriages should be ordered such that carriage 1 comes first, then 2, etc. with carriage L coming last.
Output Specification
For each test case output the sentence: 'Optimal train swapping takes S swaps.' where S is an integer.
Example Input
3
3
1 3 2
4
4 3 2 1
2
2 1
Example Output
Optimal train swapping takes 1 swaps.
Optimal train swapping takes 6 swaps.
Optimal train swapping takes 1 swaps.
31. Ejercicio 3 - UVA - 11321
Hmm! Here you are asked to do a simple sorting. You will be given N numbers and a positive integer M. You will have to sort the N numbers in
ascending order of their modulo M value.
If there is a tie between an odd number and an even number (that is their modulo M value is the same) then the odd number will precede the
even number.
If there is a tie between two odd numbers (that is their modulo M value is the same) then the larger odd number will precede the smaller odd
number and if there is a tie between two even numbers (that is their modulo M value is the same) then the smaller even number will precede
the larger even number.
For remainder value of negative numbers follow the rule of C programming language: A negative number can never have modulus greater than
zero. E.g. -100 MOD 3 = -1, -100 MOD 4 = 0 etc.
Input
The input file contains 20 sets of inputs. Each set starts with two integers N (0<N<=10000) and M (0<M<=10000) which denotes how many
numbers are within this set. Each of the next N lines contains one number each. These numbers
should all fit in 32-bit signed integer. Input is terminated by a line containing two zeroes.
Output
For each set of input produce N+1 lines of outputs. The first line of each set contains the value of N and M. The next N lines contain N numbers,
sorted according to the rules mentioned above. Print the last two zeroes of the input file in the output file also.
Sample Input Sample Output
15 3 15 3
1 15
2 9
3 3
4 6
5 12
6 13
7 7
8 1
9 4
10 10
11 11
12 5
13 2
14 8
15 14
0 0 0 0