Sunteți pe pagina 1din 303

Estructura de Datos y

Algoritmos
Cdigo de Curso: CY330
Versin 3.0

Gua del Estudiante

Libro 1: Estructura de
Datos y Algoritmos

IBM IT Education Services


Worldwide Certified Material
Informacin Sobre la Publicacin

Esta publicacin ha sido producida usando Microsoft Word 2000 y Microsoft PowerPoint
2000 para Windows.

Marcas Registradas

IBM es una marca registrada por International Business Machines Corporation.

Otras compaas, productos, y nombre de servicios pueden ser marcas registradas o


marcas de servicios de otros.

Trademarks of International Business Machines Corporation

DB2 Informix

Lotus Script Net.data

Marcas Registradas de otras Compaas

Windows, Microsoft Visual Studio Microsoft Corporation

Sybase Sybase Inc.

Edicin Enero 2008

La informacin contenida en este documento no ha sido sometida a ninguna prueba


formal de IBM y es distribuida bsicamente como es" sin ninguna garanta ya sea
expresa o implcita. El uso de esta informacin o la implementacin de cualquiera de
estas tcnicas es responsabilidad del comprador y depender de la habilidad de ste
para su evaluacin e integracin en el ambiente operacional del comprador. A pesar de
que cada tema ha sido revisado por IBM para su exactitud en una situacin especfica,
no hay garanta de obtener el mismo resultado o uno similar a ste en otra situacin.
Los compradores que intenten adaptar estas tcnicas a sus propios ambientes lo hacen
bajo su propio riesgo.

Copyright International Business Machines Corporation, 2008. All rights reserved.


Este documento no puede ser reproducido en su totalidad o en parte sin el previo
permiso escrito de IBM.

Instrucciones Especiales para la Impresin de este Curso:

No elimine pginas en blanco que puedan aparecer al final de cada unidad entre
unidades. Estas pginas fueron insertadas intencionalmente.

.
Gua del Estudiante Estructura de Datos y Algoritmos

Contenido
Descripcin del Curso ....................................................................................... 5
Descripcin de Unidades................................................................................... 7
Volumen 1: Estructura de Datos Simples ...................................................... 11
Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista
.......................................................................................................... 13
Objetivos de Aprendizaje 13
1. Introduccin 14
2. La Necesidad de Algoritmos y Estructura de Datos 14
3. Tipos de Datos y Estructura de Datos 15
4. El Rol de las Estructuras de Datos para Resolver Problemas 17
5. Tipo de Dato Abstracto Abstract Data Type (TDA) 17
6. Estructura de Datos Lista 18
7. Implementacin de una Lista como un Arreglo 21
8. Aplicaciones que Usan la Estructura de Datos Lista 32
Resumen 34
Unidad 1: Examen de Autoevaluacin 35
Respuestas de la Unidad 1: Examen de Autoevaluacin 37
Unidad 2: Lista Enlazada ................................................................................. 39
Objetivos de Aprendizaje 39
1. Introduccin a Listas Enlazadas 40
2. Operaciones en una Lista Enlazada 42
3. Encontrar el Predecesor y Sucesor en la Lista Enlazada 50
Resumen 63
Unidad 2: Examen de Autoevaluacin 64
Respuestas al la Unidad 2: Examen de Autoevaluacin 67
Unidad 3: Laboratorio de Listas Enlazadas ................................................... 69
Objetivos de Aprendizaje 69
Ejercicio de Laboratorio 70
Unidad 4: Pila.................................................................................................... 73
Objetivos de Aprendizaje 73
1. Pilas 74
2. Tipo de Dato Abstracto Pila 75
3. Implementar Pilas Usando Arreglos 78
4. Pila como Lista Enlazada 86
i
Copyright IBM Corp. 2008
Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5. Aplicaciones de Pilas 89
6. Evaluar una Expresin Postfija 103
Resumen 106
Unidad 4: Examen de Autoevaluacin 107
Respuestas de la Unidad 4: Examen de Autoevaluacin 109
Unidad 5: Laboratorio de Pila........................................................................ 111
Objetivos de Aprendizaje 111
Ejercicios de Laboratorio 112
Unidad 6: Colas .............................................................................................. 113
Objetivos de Aprendizaje 113
1. Preliminares de Cola 114
2. Implementar las Colas como Arreglos 119
3. Usar Arreglos Circulares 127
4. Colas como Listas Enlazadas 130
5. Aplicaciones de Colas 135
Resumen 137
Unidad 6: Examen de Autoevaluacin 138
Respuestas a la Unidad 6: Examen de Autoevaluacin 140
Unidad 7: Laboratorio de Colas .................................................................... 141
Objetivos de Aprendizaje 141
Ejercicio de Laboratorio 142
Volumen 2: Estructuras de Datos Avanzadas ............................................. 143
Unidad 1: Grafos ............................................................................................ 145
Objetivos del Aprendizaje 145
1. Introduccin 146
2. Preliminares de Grafos 146
3. Grafos No Dirigidos 149
4. Grafos Dirigidos 150
5. Grafos y Estructuras de Datos 152
6. Aplicaciones de Grafos 159
Resumen 162
Unidad 1: Examen de Autoevaluacin 163
Respuestas a la Unidad 1: Examen de Autoevaluacin 165
Unidad 2: rboles........................................................................................... 167
Objetivos del Aprendizaje 167
1. Introduccin 168
ii
Copyright IBM Corp. 2008
Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

2. rboles Generales 168


3. rboles Binarios 169
4. Recorrido de rboles 172
5. rbol de Bsqueda Binaria 177
6. Aplicaciones de rboles 182
7. Heaps 184
8. Aplicacin de Heaps 186
Resumen 187
Unidad 2: Examen de Autoevaluacin 188
Respuestas a la Unidad 2: Examen de Autoevaluacin 190
Unidad 3: Tcnicas Simples de Ordenamiento............................................ 191
Objetivos del Aprendizaje 191
1. Introduccin 192
2. Tcnicas Simples de Ordenamiento 192
Resumen 207
Unidad 3: Examen de Autoevaluacin 208
Respuestas a la Unidad 3: Examen de Autoevaluacin 211
Unidad 4: Laboratorio de Tcnicas Simples de Ordenamiento.................. 213
Objetivos del Aprendizaje 213
Ejercicio de Laboratorio 214
Unidad 5: Tcnicas Avanzadas de Ordenamiento....................................... 217
Objetivos del Aprendizaje 217
1. Introduccin 218
2. Ordenamiento Merge Sort (por Fusin o Mezcla) 218
3. Ordenamiento Quicksort (Rpido) 223
4. Temas Opcionales de Estudio 234
5. Algoritmos y Complejidad 234
6. Comparacin de Algoritmos de Ordenamiento 242
Resumen 248
Unidad 5: Examen de Autoevaluacin 249
Respuestas a la Unidad 5: Examen de Autoevaluacin 251
Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas............. 253
Objetivos de Aprendizaje 253
Ejercicio de Laboratorio 254
iii
Copyright IBM Corp. 2008
Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 7: Tcnicas de Bsqueda ................................................................. 257


Objetivos de Aprendizaje 257
1. Introduccin 258
2. Bsqueda Lineal o Secuencial 258
3. Bsqueda Binaria 261
4. Tablas Hash 269
5. Diferentes Funciones Hash 273
6. Mtodos de Resolucin de Colisiones 278
7. Aplicaciones de Tablas Hash 287
Resumen 289
Unidad 7: Examen de Autoevaluacin 290
Respuestas a la Unidad 7: Examen de Autoevaluacin 292
Unidad 8: Laboratorio de Tcnicas de Bsqueda ....................................... 293
Objetivos de Aprendizaje 293
Ejercicios de Laboratorio 294
Unidad 9: Laboratorio de Tablas Hash......................................................... 299
Objetivos de Aprendizaje 299
Ejercicios de Laboratorio 300

iv
Copyright IBM Corp. 2008
Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Descripcin del Curso


Nombre del Curso
Estructura de Datos y Algoritmos.
Duracin
La duracin del curso es de 40 horas de 45 minutos 30 horas efectivas.
Propsito
El curso ofrece a los estudiantes todos los conceptos relacionados con las estructuras
de Datos y Algoritmos. Comienza, con una introduccin a lo que se conoce como tipos
de Datos (TDA) y Estructuras de Datos como tal, as como aplicaciones donde se pone
en prctica dichas estructuras.

El primer volumen del curso presenta las estructuras de datos simples, comenzando
con listas implementadas como arreglos y terminando con listas enlazadas. Tambin, se
proporciona una visin general de lo que es la estructura de datos pila y cola la manera
en que pueden ser implementadas ya sea con listas o con arreglos.

El segundo volumen presenta lo que son las estructuras de datos avanzadas, el trabajo
con grafos y rboles, las diferentes aplicaciones para cada uno de ellos, as como los
diferentes recorridos para los rboles. Adicionalmente, se proporcionan las diferentes
tcnicas de ordenamiento, tanto simples como avanzadas.

Para finalizar, se explican las diferentes tcnicas de bsqueda, as como todo lo


referente a las Tablas Hash.
Audiencia
Estudiantes, Profesionales.
Prerrequisito
CY300, CY320
Objetivos
Despus de completar el curso, usted ser capaz de:
Definir los fundamentos de Estructura de Datos.
Explicar la estructura de datos lista y lista enlazada.
Describir el tipo de dato abstracto pila.
Discutir el tipo de dato abstracto cola.
Explicar las estructuras de datos avanzadas.
Discutir sobre los grafos y sus aplicaciones.
Explicar los rboles, tipos y diferentes aplicaciones.
Describir las tcnicas simples de ordenamiento.

Libro 1: Estructura de Datos y Algoritmos Descripcin del Curso 5

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Discutir las tcnicas avanzadas de ordenamiento.


Explicar las diferentes tcnicas de bsqueda.
Discutir la Tabla Hash.

Descripcin del Curso Libro 1: Estructura de Datos y Algoritmos 6

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Descripcin de Unidades
Volumen 1: Estructura de Datos Simples
Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista

En esta unidad se explica el rol de las estructuras de datos y algoritmos como bloques
de construccin en programas de computadoras, adems de la definicin de dicha
estructura de datos. Se explicar la diferencia entre un tipo de dato y una estructura de
datos. Adicionalmente, se tocan aspectos como: definir la resolucin de problemas
utilizando estructura de datos, describir las listas como un tipo de dato, discutir toda su
estructura e implementar listas como arreglos.

Unidad 2: Lista Enlazada

En esta unidad se discute la necesidad de la lista enlazada, as como las diferentes


operaciones que se pueden realizar sobre ella. Por otra parte, se discute la
implementacin de listas simplemente enlazadas, la definicin de listas doblemente
enlazadas y listas enlazadas circulares. Seguidamente, se compara la implementacin
de una lista usando arreglo y lista enlazada.

Unidad 3: Laboratorio de Listas Enlazadas

Aqu se aplican los conocimientos adquiridos sobre listas enlazadas. Adicionalmente, se


crean listas enlazadas, aparte de escribir operaciones en una implementacin de lista
como lista enlazada.

Unidad 4: Pila

En esta unidad se tocan tpicos como la definicin de la estructura de datos pila y las
diferentes operaciones que se realizan sobre dicha estructura. En tal sentido, se
describen las operaciones del TDA Pila, tambin se explica la implementacin usando
un arreglo y una lista enlazada. Para finalizar, se resuelven algunos problemas usando
pilas.

Unidad 5: Laboratorio de Pila

Este laboratorio fue diseado con la finalidad de aplicar el concepto de pila para
resolver problemas simples, crear una pila y realizar sus operaciones en C, adems de
aplicar dichas operaciones en todo tipo de aplicaciones.

Unidad 6: Colas

Esta unidad presenta la definicin de la estructura de datos cola, adems se explican


las diferentes operaciones que se pueden realizar en el TDA cola. Se discutir la
implementacin de la cola como arreglo, arreglo circular y como lista enlazada.

Libro 1: Estructura de Datos y Algoritmos Descripcin de Unidades 7

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 7: Laboratorio de Colas

En esta unidad se dispone aplicar los conceptos de TDA colas en cualquier problema,
crear cualquier tipo de cola y realizar operaciones sobre dicho TDA.
Volumen 2: Estructura de Datos Avanzadas
Unidad 1: Grafos

Se presentar la definicin de grafos dirigidos y no dirigidos. Por otra parte, se explican


las propiedades de los grafos no dirigidos. Se aprender a representar grafos como un
conjunto, una tabla de adyacencia y una lista de adyacencia, adems de definir
trminos asociados con grafos y aplicaciones sobre ellos.

Unidad 2: rboles

En esta unidad se discute la definicin de un rbol como estructura de datos, as como


los diferentes tipos de rboles: rboles binarios, rboles de bsqueda binaria y rboles
en general. Se busca explicar los tres mtodos de recorrido para un rbol binario, definir
un heap y distinguir entre un heap mnimo y un heap mximo.

Unidad 3: Tcnicas Simples de Ordenamiento

Se presentar en esta unidad, una visin general de las tcnicas de ordenamiento,


adems de explicar el algoritmo de ordenamiento por insercin, burbuja y seleccin.

Unidad 4: Laboratorio de Tcnicas Simples de Ordenamiento

En este laboratorio se debern escribir algoritmos de ordenamiento en una forma simple


y eficiente, por otra parte se busca distinguir entre los diferentes algoritmos de
ordenamiento y modificarlos para ajustarlos a una situacin particular.

Unidad 5: Tcnicas Avanzadas de Ordenamiento

En esta unidad se explicarn las tcnicas de merge sort (ordenamiento por fusin) y
quicksort (ordenamiento rpido), lo cual incluye escribir un algoritmo para desarrollar
cada una de estas tcnicas.

Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas

En este laboratorio debern escribir algoritmos de ordenamiento eficientes y simples


basados en las tcnicas aprendidas. La finalidad es distinguir entre los diferentes
algoritmos de ordenamiento y adaptarlos a una aplicacin en particular.

Descripcin de Unidades Libro 1: Estructura de Datos y Algoritmos 8

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 7: Tcnicas de Bsqueda

Se estudiar, en esta unidad, las diferentes tcnicas de bsqueda para entender la


diferencia entre bsqueda interna y externa. Se describir la forma de desarrollar un
algoritmo mediante el uso de la tcnica de bsqueda lineal o binaria. En tal sentido, se
explicar el uso de hashing para insertar y localizar elementos en una tabla hash,
aunado a los diferentes mtodos para la resolucin de colisiones hash.

Unidad 8: Laboratorio de Tcnicas de Bsqueda

En esta unidad se deben aplicar los conceptos aprendidos sobre bsqueda en cualquier
desarrollo de aplicaciones y realizar algoritmos de bsqueda lineal y binaria.

Unidad 9: Laboratorio de Tablas Hash

En el siguiente laboratorio se aplicarn todos los conocimientos aprendidos, con la


finalidad de crear una tabla hash y sus usos en diferentes aplicaciones. Del mismo
modo, se pondrn en prctica las tcnicas aprendidas en otras aplicaciones.

Libro 1: Estructura de Datos y Algoritmos Descripcin de Unidades 9

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Volumen 1: Estructura de Datos Simples

Libro 1: Estructura de Datos y Algoritmos Descripcin de Unidades 11

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 1: Fundamentos de Estructura de


Datos y Estructura de Datos Lista
Objetivos de Aprendizaje
Al final de esta unidad, ud. ser capaz de:
Explicar el rol de las estructuras de datos y algoritmos como bloques de
construccin en programas de computadora.
Definir estructura de datos.
Discutir las diferencias entre un tipo de dato y una estructura de dato.
Explicar el rol de las estructuras de datos para resolver problemas.
Describir la lista como Tipo de Dato Abstracto.
Discutir la estructura de lista de datos.
Explicar cmo implementar una lista como un arreglo.

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 13

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. Introduccin
En este curso se discutirn dos aspectos importantes del esfuerzo de programacin, los
cuales son: las estructuras de datos y los algoritmos. Una combinacin correcta de
estructuras de datos apropiada y algoritmos eficientes dan como resultado buenos
programas. Se comenzar la discusin de estructuras de datos con las listas, y se
proceder a aprender los diferentes algoritmos de bsqueda y ordenamiento. Antes de
continuar estudiando las diferentes estructuras de datos, se discutir brevemente la
necesidad de algoritmos y estructuras de datos, las diferencias entre tipo de dato y
estructuras de datos, adems del rol de las estructuras de datos para la solucin de
problemas.

2. La Necesidad de Algoritmos y Estructura de Datos


Un algoritmo es un conjunto de instrucciones no ambiguo y secuencial que ayudan a
resolver un problema dado. Considere un ejemplo para entender los algoritmos. Para
buscar el nombre de una ciudad dada en una lista de nombres de ciudades, se escribir
un programa en C que use el siguiente algoritmo:
1) Leer la lista de nombres de ciudades y almacenarlos en un arreglo nombres.
2) Leer el nmero de nombres de ciudades en la lista y almacenarlo en una variable
total.
3) Leer el nombre de la ciudad que va a buscarse y almacenarlo en nombreciudad.
4) Colocar un contador p a 0.
5) Si el nombre de la ciudad buscada es el mismo que el elemento nmero p en la
lista, entonces mostrar el mensaje El nombre de la ciudad se ENCUENTRA en la
lista. Ir al paso 9.
6) Incrementar p en 1. Revisar si p es igual a total.
7) Si p es igual a total, entonces mostrar El nombre de la ciudad NO SE
ENCUENTRA en la lista. Ir al paso 9.
8) Si p no es igual a total, entonces ir al paso 5.
9) Fin del algoritmo.
El algoritmo anterior es simple pero revela dos elementos esenciales en la resolucin de
problemas que son: el mecanismo de almacenamiento que se usa para almacenar los
datos y el mtodo que se usa para resolver el problema. Por lo tanto, al proveer una
solucin al problema de buscar el nombre de una ciudad en una lista, los dos aspectos
esenciales son:
El mecanismo de almacenamiento para la lista. La pregunta que debe
responderse es: Cmo se almacena la lista de nombre de ciudades?
Los pasos requeridos para resolver el problema. La pregunta aqu es: Cul es
el mtodo escogido para proveer la solucin?

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 14

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

En este ejemplo se ha usado un mtodo simple de almacenamiento, es decir, un


arreglo. Sin embargo, para la solucin de problemas ms complicados y grandes, la
decisin del mtodo de almacenamiento es crucial. As, se puede decir que los dos
elementos ms importantes en un esfuerzo para resolver un problema grande son:
Estructuras de datos: El mecanismo de almacenamiento.
Algoritmos: El mtodo usado para proveer la solucin que se da por medio de un
conjunto de pasos secuenciales.
Las estructuras de datos que sern estudiadas en este curso son: listas, pilas, colas,
grafos y rboles. Casi todas las estructuras de datos tienen algoritmos asociados con
ellas. Estos algoritmos permiten que algunas de las operaciones bsicas e importantes
sean realizadas en estructuras de datos. Algunas de estas operaciones son insertar,
borrar y buscar. Las nomenclaturas usadas para estas operaciones pueden diferir
para cada estructura de datos. A continuacin se aprender acerca de las diferencias
bsicas entre tipos de datos y estructuras de datos.

3. Tipos de Datos y Estructura de Datos


En esta seccin, se aprender qu es un tipo de dato. Tambin se entender qu son
estructuras de datos y cmo difieren de los tipos de datos.

3.1 Tipo de Dato

Cuando surge la pregunta Qu es un tipo de dato?, la respuesta tpica es integer,


char, y float. Estos se refieren a diferentes clases de tipos de datos que
satisfacen las propiedades de un tipo de dato. Por definicin, un tipo de dato es un
conjunto de valores que una variable de ese tipo puede tomar y las operaciones
permitidas sobre ella. El trmino tipo de dato se usa normalmente en referencia a un
lenguaje de programacin. La definicin anterior tiene dos partes importantes, un
conjunto de valores y las operaciones que estos valores pueden tomar. Ver Tabla 1.1.
Nota: Los nombres de los tipos de datos usados no reflejan ningn nombre que
pertenezca a un lenguaje de programacin especfico.
Tipos de
Conjunto de Valores Operaciones
Dato
-valor mnimo negativo
Entero
+valor mximo positivo (ej. 128 a +, -, *, /, y %
(Integer)
+127).
Flotante Dependiendo del rango y precisin
+, -, *, y /
(Float) (eg. 0.9, 1.0, 2341.5123, etc.).
Booleano Verdadero (true),
AND, OR, y NOT
(Boolean) Falso (false)
Letras del alfabeto (ej., a, b, c A, B, Depende del lenguaje de
Carcter C,....) programacin. Algunos ejemplos son
(Character) Smbolos especiales como *, (, &, ^, de conversin a ASCII,
etc. predecesores y sucesores.
Tabla 1.1: Tipo de Datos, Conjunto de Valores y Operaciones

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 15

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

3.2 Estructuras de Datos

En el ejemplo anterior, se trat la bsqueda del nombre de una ciudad dada en una
lista. All, se us un arreglo para almacenar la lista. En la mayora de los lenguajes de
programacin, una lista simple ser almacenada como un arreglo. Una lista de enteros
ser representada como un arreglo de enteros, una lista de valores Booleanos como un
arreglo de Boolean y as sucesivamente.
Por ejemplo, se pueden almacenar los detalles de un estudiante como sigue:
Nombre del estudiante (representado como un arreglo de caracteres).
Edad del estudiante (representada como un entero).
Notas obtenidas por el estudiante (representadas como un flotante).
Normalmente, estos se refieren como estructuras de datos, ya que se desarrolla una
estructura agrupando diferentes tipos de datos juntos. El trmino estructura de dato se
usa normalmente cuando se refiere a una coleccin de datos que estn organizados de
alguna u otra manera.

Una estructura de datos, puede as, ser definida como una coleccin de entidades
pertenecientes a tipos de datos diferentes que resulta en la organizacin de piezas de
datos interrelacionadas. Las estructuras de datos tambin tienen un conjunto de valores
y operaciones definidas en estos valores.

Para almacenar las tres secciones de datos de un estudiante, el mecanismo de


almacenamiento que ser adoptado es una estructura en C. Los lenguajes como Pascal
y Ada usan registros para el mismo propsito. Para soportar una lista de estudiantes se,
se usar un arreglo para representar la lista en C. As se tendr un arreglo de
estructuras de estudiante. Ambos arreglos y estructuras son referidos como tipos de
datos estructurados en el lenguaje de programacin, cuando son soportados
directamente por el lenguaje de programacin. Sin embargo, en un nivel conceptual, los
arreglos son slo estructura de datos. Por otro lado, las estructuras de datos son
aquellas que no se encuentran directamente soportadas por el lenguaje de
programacin. Ellos son declarados y definidos por los programadores. Por lo que a
veces son referidos como tipos de datos definidos por el usuario. Para el propsito de la
discusin en este curso, solo se usar el trmino de estructura de datos. Se discutirn a
continuacin, las siguientes estructuras de datos y sus operaciones:
Lista.
Pila.
Cola.
Grafo.
rbol.
Estas estructuras de datos tienen operaciones apropiadas definidas sobre ellas. Se
aprender acerca de esto en las prximas unidades de este curso.

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 16

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

4. El Rol de las Estructuras de Datos para Resolver


Problemas
Las estructuras de datos y los algoritmos juegan un rol significativo en la resolucin de
problemas y el diseo de programas. Los roles estn bastante entrelazados, como se
muestra a continuacin:
La seleccin de las estructuras de datos que se pueden usar para resolver un
problema es una de las mayores fuentes de variabilidad en el diseo de
algoritmos.
La seleccin de una estructura de datos puede incidir sobre la facilidad o no con
la cual un algoritmo se puede escribir.
La seleccin de una estructura de dato puede aumentar o disminuir el
requerimiento de espacio de almacenamiento y otros recursos en una
computadora.
La seleccin de una estructura de dato puede aumentar o disminuir el tiempo de
ejecucin de un algoritmo en una computadora.
Las estructuras de datos y algoritmos van de la mano como los principales
bloques de construccin de programas.
De acuerdo a Niklaus Wirth, el diseador de los lenguajes Pascal y Modula-2,
Estructura de Datos + Algoritmos = Programas
Esto es verdad, ya que son las estructuras de datos y algoritmos los que hacen los
programas.

Para comprender la diferencia de estructuras de datos, es esencial entender el Tipo de


Dato Abstracto TDA (en ingls ADT Abstract Data Type). En la siguiente seccin, se
discuten los TDA.

5. Tipo de Dato Abstracto Abstract Data Type (TDA)


Anteriormente, se aprendi lo que es un tipo de dato. Ampliando el concepto de un tipo
de dato, un TDA se refiere a entidades de almacenamiento de datos y las operaciones
definidas en esas entidades. Por lo tanto, se dice que un TDA es simplemente una
coleccin de operaciones. Ellas pueden ser vistas como notaciones matemticas para
describir las operaciones sobre entidades de almacenamiento de datos, sin hacer
nfasis en los aspectos de implementacin de las operaciones.

Al considerar una estructura de datos como un TDA, se obtiene una clara


representacin de las operaciones realizadas sin recarga en los detalles de la
implementacin. Ejemplos de las estructuras de datos ms usadas y algunas de sus
operaciones a nivel TDA se presentan a continuacin:
Lista
- Insertar un elemento.

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 17

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

- Borrar un elemento.
- Encontrar un elemento.
- Mostrar elementos.
Conjunto
- Unin de dos conjuntos.
- Interseccin de dos conjuntos.
- Diferencia entre dos conjuntos.
Pila
- Insertar (push) un elemento.
- Eliminar (pop) un elemento.
- Tope de la pila.
Cola
- Aadir un elemento.
- Quitar un elemento.
- Frente de la cola.
- Longitud de la cola.
rbol
- Aadir un nodo.
- Borrar un nodo.
- Recorrer un rbol.
En los ejemplos anteriores, lista, conjunto, pila, cola y rbol son entidades de
almacenamiento de informacin. Las operaciones definidas sobre cada una de estas
entidades varan dependiendo del propsito para los cuales las entidades se crearon. A
nivel de TDA, las operaciones se especifican sin dar detalles sobre cmo se
implementan.

Se comenzar la discusin de estructura de datos con la estructura de datos lista.

6. Estructura de Datos Lista


El uso comn del trmino lista se refiere a una coleccin lineal de elementos de datos.
A continuacin se presentan tres ejemplos comunes de listas:
Lista por hacer.
Lista de compra.
Lista de comestibles.
Una lista se puede definir como una serie de cero o ms elementos, donde cada
elemento pertenece a un tipo dado. Una lista puede tener n elementos, como se
muestra a continuacin:

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 18

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

elem1, elem2, elem3 elemn


Aqu n >= 0. n se denomina la longitud de la lista. elem1 es el primer elemento de la
lista, mientras elemn es el ltimo elemento de la lista. Una lista se dice que est vaca
cuando el nmero de elementos, n, es cero.

Las listas son estructuras de datos que se puede expandir o contraer. Se puede
insertar, eliminar y acceder elementos en una lista. Tambin, se puede dividir una lista,
o unir dos listas.

6.1. La Lista como un Tipo de Dato Abstracto

Una lista puede ser vista como un TDA al definir un conjunto de operaciones sobre ella.
Unas cuantas operaciones tpicas definidas en una lista son:
Nueva
Insertar
Borrar
Encontrar
Obtener
Esvacio
Para entender las semnticas de las operaciones anteriores, se tienen las siguientes
variables:
Lista: La lista.
elem: Elemento en la lista.
pos: Posicin donde un elemento reside en la lista.
Usando estas tres variables, se van a entender las operaciones en una lista que se dan
a continuacin:
nueva(lista): Crea y retorna una nueva lista.
insertar(lista, elem): Inserta elem en la lista.
borrar(lista, pos): Borra un elemento en una lista en la posicin pos.
Si la lista est vaca o pos no existe en la lista, entonces la operacin
resulta en un error.
encontrar(lista, elem): Busca elem en la lista y retorna la posicin en
la que elem se encuentra.
obtener(lista, pos): Obtiene el elem encontrado en la posicin pos de la
lista. Si pos es menor que 1 mayor que el nmero de elementos de la
lista, la operacin resulta en un error.
esvacio(lista): Retorna verdadero si la lista es vaco, de lo contrario
retorna falso.

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 19

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Las operaciones nueva e insertar son dos operaciones bsicas de la lista que
generan todas las nuevas listas posibles. De aqu que, estas operaciones se denominen
operaciones primitivas. Una operacin primitiva es aquella que se puede usar para
definir todas las otras operaciones de una estructura de datos. Para una estructura de
lista de datos, las operaciones primitivas son nueva e insertar.

Para entender esto, se define la operacin esvacio usando nueva e insertar.

Se sabe que la operacin esvacio toma un argumento y el argumento es una lista.


De la lista de operaciones que se dio anteriormente, se sabe que nueva es una
operacin que crea y retorna una nueva lista. Se pasa ahora la operacin nueva como
un argumento a esvacio.
esvacio(nueva)
La nueva lista retornada por una operacin nueva es una lista vaca, ya que todava no
se han aadido elementos. As, se puede decir:
esvacio(nueva) = verdadero
Ahora, se definir esvacio usando otra operacin primitiva, insertar. La operacin
insertar toma dos argumentos, llamados, lista y elem. Retorna una nueva lista
con elem insertado en la lista. Si se pasa la operacin insertar como un argumento a
esvacio, entonces se puede escribir esvacio como sigue:
esvacio(insertar(lista, elem)) = falso
Considere dos escenarios cuando una insercin toma lugar.
Lista es vaca: Si una lista es vaca, la operacin insertar aade el primer
elemento en la lista y retorna la lista con el nuevo elemento aadido.
Lista no es vaca: Si una lista ya contiene elementos, la operacin insertar
aade el nuevo elemento y retorna la lista con el nuevo elemento aadido.
En cualquier caso, la operacin esvacio recibe una lista que no es vaca. En la primera
instancia, es una lista con tan solo un elemento, y en la segunda, es una lista con ms
de un elemento. Se observa entonces que esvacio(insertar(lista,elem))
siempre retorna falso. Definiendo esvacio usando eliminar o cualquier otra operacin
no-primitiva no ser posible.

Las sentencias anteriores, llamadas:


esvacio(nueva) = verdadero
esvacio(insertar(lista,elem)) = falso
Define las reglas de las operaciones en una estructura de datos. Estos se denominan
axiomas y esas definiciones se conocen como definiciones axiomticas. Los axiomas
ayudan a tener una idea ms clara de la estructura de datos sin ir a los detalles de

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 20

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

implementacin. Se discutirn ms axiomas, relacionados a las estructuras de datos de


pila y cola, en la Unidad 4 y Unidad 6 de este volumen.

La operacin borrar no se usa como una operacin para generar todas las listas, de
all que no es una operacin primitiva. La operacin borrar no retorna una nueva lista,
solamente quita uno de los elementos existentes de la lista y retorna una lista
modificada.

7. Implementacin de una Lista como un Arreglo


Considerar la siguiente lista de ciudades en un arreglo:
Albany.
Bethesda.
Bloomington.
Cincinnati.
Dayton.
Denver.
Detroit.
Tarrytown.
Hay ocho elementos inicialmente en la lista y se quiere aadir la ciudad Connecticut
a la lista. Se debe insertar la ciudad en el orden correcto y mover todos los elementos
que siguen en la lista. Ver Figura 1.1.

Figura 1.1: Insercin en una Lista

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 21

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ahora se quiere borrar una ciudad de la lista, esto crea un hueco en la lista. Por esto, se
debe mover todos los elementos de abajo hacia arriba un paso. En la Figura 1.2 se ha
borrado Dayton y se han movido los elementos una celda hacia arriba.

Figura 1.2: Borrar de una Lista

A continuacin se aprender acerca de la implementacin de una lista usando un


arreglo. Las operaciones que se discuten son:
Crear una nueva lista.
Insertar un elemento en una lista.
Eliminar un elemento de una lista.
Buscar un elemento en una lista.
Encontrar el sucesor y predecesor de un elemento en una lista.
Determinar si una lista es vaca.
La implementacin de las operaciones anteriores en una lista se har para una lista de
cadenas con una sola palabra. En la solucin que se presenta para las diferentes
operaciones, no se preocupe acerca del ordenamiento de las palabras en la lista, ya que
todava no se ha visto ordenamiento de elementos en una lista. As, la lista contendr un
conjunto de palabras sin ningn orden.

Primero, se define el tamao de una lista y la cadena. A continuacin, se crea un tipo de


dato definido por el usuario List_Array que contiene dos componentes:
Count: Para mantener registro del nmero de elementos en la lista.

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 22

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

List: Un arreglo para guardar las palabras.


7.1 Definiciones Bsicas

El cdigo en C empieza aqu


1. #define LISTMAX 100 /* Limite mximo */
2. #define STRINGSIZE 30
3. #include "stdlib.h"
4. #include "stdio.h"
5. /* Definicin Type para una lista*/
6. typedef struct {
7. int count; /* Nro. de elementos en
list(lista) */
8. char list[LISTMAX][STRINGSIZE];
9. } List_Array;
El cdigo C termina aqu

7.2 Crear una Nueva Lista

Se escribe una operacin para crear una lista nueva (new).

El cdigo en C empieza aqu


1. /* Crear una lista. */
2. void newList(List_Array *list_ptr){
3. int k;
4. list_ptr->count = 0; /* No hay elementos*/
5. for(k = 0; k < LISTMAX; k++)
6. /* Inicializar con un carcter null */
7. strcpy(list_ptr->list[k],"\0");
8. }
El cdigo C termina aqu

La funcin newList inicializa la lista colocando el contador a 0 y asignando


caracteres nulos (null) a todas las posiciones en el arreglo. Note que este paso de
inicializar con un carcter null no es estrictamente necesario, siempre y cuando se
escriban las otras funciones cuidadosamente, adems que nunca se referencien
posiciones que no han sido inicializadas. Sin embargo, es una buena prctica inicializar
variables.

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 23

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

7.3 Insertar un Elemento en la Lista

El cdigo en C empieza aqu


1. /* Para insertar un elemento en la lista */
2. int insertElement(List_Array *list_ptr, char *element)
{
3. if(list_ptr->count == LISTMAX)
4. return (-1); /* Tamao mximo alcanzado
*/
5. else {
6. strcpy(list_ptr->list[list_ptr->count], element);
7. list_ptr->count++; /* Un elemento mas */
8. return (1); /* retorna xito */
9. }
10. }
El cdigo C termina aqu

Es una excelente prctica revisar primero por errores y luego seguir con la funcin. Si el
nmero de elementos en la lista es igual a LISTMAX retornamos 1 a la funcin que lo
invoc. La funcin llamada puede revisar este valor y si se requiere manejar el error de
la mejor manera. Si se requiere hacer una insercin, simplemente se debe copiar el
elemento de un arreglo al final. Se incrementa la variable count y se sale de la funcin.

7.4 Eliminar un Elemento de una Lista

Ahora se implementa la funcin deleteElement que elimina un elemento de la lista. El


algoritmo es simple. Toma como entrada un puntero o apuntador a una lista y la
posicin de la cual el elemento debe ser eliminado. El proceso de eliminacin deja un
espacio vaco en esa posicin. Por esto, los elementos que siguen en la lista deben ser
movidos. La variable count es decrementada. El segmento de cdigo se da a
continuacin.

El cdigo en C empieza aqu


1. /* Eliminar un elemento en la lista dada su posicin */
2. int deleteElement(List_Array *list_ptr, int pos) {
3. int k;
4. /* Revisar si pos existe y errores */
5. if (pos < 0 || pos > list_ptr->count-1)
6. return (-1); /* error */
7. else {

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 24

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

8. /* Mueve todos los elementos */


9. for (k = pos; k < list_ptr->count - 1; k++)
10. strcpy(list_ptr->list[k], list_ptr-
>list[k+1]);
11. list_ptr->count--;
12. return (1); /* eliminacin con xito */
13. }
14. }
El cdigo C termina aqu

Si pos < 0 pos > count-1, implica que es una posicin invlida. Por lo que, se
retorna de la funcin con -1.

7.5 Buscar un Elemento en la Lista

La funcin find (encontrar) toma un elemento como entrada, localiza la posicin de


ese elemento en la lista y retorna la posicin donde el elemento se encuentra en la lista.

El cdigo en C empieza aqu


1. /* Encontrar un elemento en la lista */
2. int find(List_Array *list_ptr, char *element) {
3. int k = 0;
4. while (k <= list_ptr->count - 1)
5. /* Revisar por el nombre en k */
6. if (!strcmp(list_ptr->list[k], element))
7. return (k+1);
8. else
9. k++;
10. return (-1); /* Elemento no encontrado */
11. }
El cdigo C termina aqu

Esto es directo. Simplemente se revisa cada elemento del arreglo con el elemento
buscado. Si el elemento es encontrado, se retorna la posicin del elemento en la lista.
Aqu, se retorna k+1, ya que el arreglo empieza en 0. Si el elemento no es encontrado,
se retorna -1.

7.6 Encontrar el Sucesor y Predecesor de un Elemento en una Lista

A continuacin se dan las implementaciones para encontrar el sucesor y predecesor de


una posicin dada en una lista. Estas funciones toman una posicin en la lista como
Libro 1: Estructura de Datos y Algoritmos
Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 25

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

entrada y retorna el elemento que es el sucesor o predecesor de esa posicin. Las


funciones realizan revisiones apropiadas para mostrar un mensaje cuando la posicin
es el primer elemento o el ltimo elemento de la lista.

El cdigo en C empieza aqu


1. /* Encuentra el elemento sucesor dada una posicin en
la lista */
2. char * succ(List_Array *list_ptr, int pos) {
3. /* Revisar errores */
4. if (pos < 0 || pos > list_ptr->count-1) {
5. printf("\nSucesor - Error de entrada: No existe \
6. tal posicin en la lista\n");/* Error */
7. return (NULL);
8. }
9. else
10. if (pos == list_ptr->count-1) {
11. printf("No existe sucesor para el ltimo \
12. elemento en la lista!\n");
13. return (NULL);
14. }
15. else
16. return (list_ptr->list[pos + 1]);
17. }
18.
19. /* Encuentra el elemento predecesor dada una posicin
en la lista */
20. char * pred(List_Array *list_ptr, int pos) {
21. /* Revisar errores */
22. if (pos < 0 || pos > list_ptr->count-1) {
23. printf("\nPredecesor - Error de entrada: No
existe \
24. esa posicin en la lista \n");/* Error */
25. return (NULL);
26. }
27. else
28. if (pos == 0) {
29. printf("No existe predecesor para el primer
\

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 26

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

30. elemento en la lista!\n");


31. return (NULL);
32. }
33. else
34. return (list_ptr->list[pos - 1]);
35. }
El cdigo C termina aqu

Las dos funciones anteriores son simples de entender. Se hace una revisin para
determinar si la posicin de entrada est dentro del rango. En el caso de la funcin del
sucesor, se revisa para determinar si la posicin de entrada es la ltima posicin en la
lista y de ser as, se genera un mensaje apropiado. Si no, se retorna el elemento en la
siguiente posicin en la lista.

Para la funcin predecesora, se hace una revisin si la posicin de entrada es igual a la


primera posicin en la lista. De ser as, se genera un mensaje apropiado, de lo contrario
se retorna el elemento en la posicin anterior.

7.7 Determinar si la Lista est Vaca


En esta operacin, se revisa una lista de entrada para determinar si est vaca.

El cdigo en C empieza aqu


1. /* Encontrar si la lista es vaca o no */
2. int isEmpty(List_Array *list_ptr) {
3. if (list_ptr->count == 0)
4. return (1); /* lista es vaca */
5. else
6. return (0); /* lista no es vaca */
7. }
El cdigo C termina aqu

El campo count se puede revisar para determinar si una lista est vaca o no. Tambin,
se da a continuacin la funcin que retorna el nmero de elementos en la lista.
/* Encontrar el nmero de elementos en una lista */
int noOfElements(List_Array *list_ptr) {
return list_ptr->count;
}
Se escribe ahora la funcin main para invocar las diferentes operaciones definidas
sobre la estructura de datos lista.

El cdigo en C empieza aqu


Libro 1: Estructura de Datos y Algoritmos
Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 27

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. main() {
2. List_Array words;
3. char *string = (char *) malloc(STRINGSIZE *
sizeof(char));
4. int i, position,value;
5. newList(&words); // Crea una nueva lista
6. printf("Ingrese una lista de palabras, termine con la
\
7. palabra 'over':\n");
8. do {
9. scanf("%s",string);
10. /* No se quiere almacenar la palabra over */
11. if (strcmp(string,"over"))
12. insertElement(&words, string);
13. } while (strcmp(string,"over"));
14. //Muestra todas las palabras en la lista despus de la
insercin
15. if (isEmpty(&words)) {
16. printf("No hay palabras en la lista!\n");
17. exit(0); // Sale si no hay palabras en la lista
18. }
19. else {
20. printf("\nLista de palabras despus de las
inserciones:\n");
21. for (i = 0; i < noOfElements(&words); i++)
22. printf("%s\n", words.list[i]);
23. printf("\n");
24. }
25. // Obtiene la posicin cuyos elementos van a ser
eliminados
26. do {
27. printf("\nIngrese la posicin para eliminar el \
28. elemento de: ");
29. scanf("%d", &position);
30. if (position < 1 || position >
noOfElements(&words))
31. printf("\nError de entrada: Posicin fuera
\

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 28

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

32. de rango!\n");
33. } while (position < 1 || position >
noOfElements(&words));
34. // Elimina un elemento
35. // Pasamos la posicin -1 a la funcin de eliminar
36. // Ya que arreglos en C++ arrays tiene ndices de 0 a
n-1
37. value = deleteElement(&words, position-1);
38. if (value == -1)
39. printf("\nError de entrada: No existe esa posicin \
en la lista\n");
40. printf("\n");
41.
42. if (isEmpty(&words)) {
43. printf("No hay palabras en la lista!\n");
44. exit(0); // Sale si no hay palabras en la lista
45. }
46. else {
47. //Muestra todas las palabras en la lista despus de la
insercin
48. printf("Lista de palabras despus de
eliminacin:\n");
49. for (i = 0; i < noOfElements(&words); i++)
50. printf("%s\n", words.list[i]);
51. }
52. // Encuentra un elemento en la lista
53. printf("\nIngrese el elemento a buscar en la lista:
");
54. scanf("%s", string);
55. value = find(&words, string);
56. if (value == -1)
57. printf("\nElemento %s no se encontra en lista!\n",
string);
58. else
59. printf("\nEl elemento se encuentra en posicin %d
\
60. en la lista!\n", value);
61. // Obtiene una posicin de predecesor y sucesor
62. // a ser encontrados
Libro 1: Estructura de Datos y Algoritmos
Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 29

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

63. do {
64. printf("\nIngrese la posicin en la lista cuyo \
65. predecesor y sucesor se va a encontrar: ");
66. scanf("%d", &position);
67. if (position < 1 || position >
noOfElements(&words))
68. printf("\nError de entrada: Posicin fuera
\
69. de rango!\n");
70. } while (position < 1 || position >
noOfElements(&words));
71. if (isEmpty(&words))
72. printf("\nError de entrada: No existe esa
posicin \ en la lista\n");
73. printf("\n");
74. // Encontrar el predecesor y sucesor en la lista
75. string = pred(&words, position-1);
76. if (string)
77. printf("El predecesor es: %s\n", string);
78. string = succ(&words, position-1);
79. if (string)
80. printf("El sucesor es: %s\n", string);
81. } /* Fin de la funcin main */
El cdigo C termina aqu

La funcin main contiene un simple pedazo de cdigo, para revisar cada funcin escrita
anteriormente. El programa completo de la estructura datos lista est listo cuando se
combina el main, las diferentes operaciones implementadas sobre la lista, los
#include requeridos y los prototipos de las funciones. La entrada y salida del
programa anterior es proporcionada a continuacin.

Entrada:
Ingrese una lista de palabras, termine con la palabra
'over':
program
computer
code
lines
algorithm
list

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 30

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

stack
over
Salida:
Lista de palabras despus de las inserciones:
program
computer
code
lines
algorithm
list
stack

Ingrese la posicin para eliminar el elemento de: 2

Lista de palabras despus de eliminacin:


program
code
lines
algorithm
list
stack

Ingrese el elemento a buscar en la lista: list

El elemento se encuentra en posicin 5 en la lista!

Ingrese la posicin en la lista cuyo predecesor y sucesor


se va a encontrar: 1

No existe predecesor para el primer elemento en la lista!


El sucesor es: code
Se asegura que no se haga ningn procesamiento cuando la lista est vaca. Tambin
es requisito revisar los valores de entrada de una posicin. Si est ms all del rango,
se hace un bucle hasta que se ingrese una posicin que est dentro del rango. Tales
verificaciones se pueden modificar para adecuarse a las necesidades de la aplicacin.

Resumen de las experiencias al implementar la estructura de datos lista usando un


arreglo:

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 31

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Al momento de escribir la aplicacin, el tamao del arreglo debe estar


determinado. Esto acta como una limitacin muchas veces.
La insercin y eliminacin de elementos requiere mover hacia arriba o hacia
abajo los elementos en el arreglo.
El tamao es predeterminado y permanece esttico en la implementacin de una
lista en el arreglo. Esto se denomina estructura de datos esttica.

8. Aplicaciones que usan la Estructura de Datos Lista


Las aplicaciones que necesitan almacenar elementos de una manera lineal usan la
estructura de datos Lista. Si la aplicacin tiene un tamao predeterminado para la lista,
entonces el mecanismo de implementacin que normalmente se usa es un arreglo. Las
siguientes son algunas de las aplicaciones que usan una lista como estructura de datos:
Representacin y operaciones aritmticas en enteros sper largos: La
representacin de enteros se hace usualmente en un nmero fijo de bytes,
usando la forma de complemento a 2. La mayora de las implementaciones
permiten representacin de enteros en un byte, dos bytes, cuatro bytes y hasta
ocho bytes. Con una representacin en ocho bytes, el entero positivo ms largo
que se puede representar es 263 1. Suponiendo que se quiere trabajar con
enteros que tienen un nmero grande de dgitos, por ejemplo 75 dgitos que son
enteros sper largos (long integers). Las listas ayudan a representar y realizar
operaciones aritmticas sobre dichos nmeros.
Representacin y operaciones polinomiales: Las listas se pueden usar para
representar polinomios y realizar operaciones sobre ellos. Los polinomios se
representan en listas tan slo guardando los coeficientes y la potencia.
Popurr de listas:
- Listas de votantes en una ciudad.
- Lista de cosas por comprar.
- Lista de estudiantes en un curso.
- Lista de empleados en una compaa.
Planificacin de tareas: Se pueden emplear listas para representar y planificar
tareas, ya sea una tarea a ser llevada a cabo en una computadora o una lista
personal de tareas. Un planificador de tareas es un buen ejemplo de una
aplicacin de lista.
Simulacin de colas usando listas: Las listas se usan para simular colas.
Muchas implementaciones de colas hacen uso de listas. Una de las aplicaciones
ms significativas de simulacin de colas es una simulacin del trfico de la red.
Bioinformtica: Las secuencias de genes se pueden almacenar como listas. Se
pueden tener aplicaciones para calcular las subsecuencias comunes ms largas.
stas se usan en aplicaciones de comparacin de genes.
Aplicaciones de procesamiento de texto: En aplicaciones de procesamiento
de texto, el texto de entrada se puede representar como una lista. Se pueden
realizar varias operaciones, como encontrar la frecuencia de ocurrencia de

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 32

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

letras, palabras de diferentes longitudes y sentencias. Se pueden computar


diferentes ndices para facilitar la lectura.
Implementaciones de conjuntos: Las listas se usan para representar conjuntos
de operaciones sobre conjuntos.
Aplicaciones en sistemas operativos
- Procesar listas.
- Administracin de paginacin de memoria.
Para aplicaciones de las que no se sabe el tamao por adelantado, se requiere una
implementacin dinmica de una lista. En la Unidad 2: Listas Enlazadas, se estudian
este tipo de listas, que permiten crear dinmicamente una lista, adems de incrementar
y decrementar el tamao de la lista en tiempo de ejecucin.

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 33

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que ha completado esta unidad, Ud. debe ser capaz de:
Explicar el rol de estructuras de datos y algoritmos como bloques de
construccin en la mayora de programas de computadoras.
Introducir el concepto de estructura de datos.
Discutir las diferencias entre un tipo de dato y una estructura de datos.
Explicar el rol de estructura de datos para resolver problemas.
Discutir la estructura de datos lista.
Describir la lista como Tipo de Dato Abstracto.
Explicar cmo implementar una lista como un arreglo.

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 34

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 1: Examen de Autoevaluacin


1) Tipo de dato y estructura de datos significan lo mismo.
a) Verdadero
b) Falso

2) Cul de los siguientes provee el TDA?


a) Operaciones
b) Implementacin para operaciones
c) Ambos (a) y (b)
d) Ninguna de las anteriores

3) Cul de las siguientes son los principales ingredientes de cualquier esfuerzo para
resolver problemas?
a) Algoritmos
b) Estructura de datos
c) Ambos (a) y (b)
d) Ninguna de las anteriores

4) Una lista es una coleccin lineal de elementos de datos que pueden estar
ordenados o desordenados.
a) Verdadero
b) Falso

5) Una lista con cero elementos es tambin una lista vlida.


a) Verdadero
b) Falso

6) Qu operacin hace la funcin succ sobre el ltimo elemento de una lista dada?
a) El ltimo elemento
b) Un error

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 35

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

7) Cul es la desventaja de implementar una lista como un arreglo?


a) El tamao de la lista es finito
b) El tamao de la lista no puede ser extendido
c) La insercin de un elemento requiere que los elementos de las posiciones
subsecuentes se desplacen hacia abajo.
d) Todas las anteriores

8) Cmo se llama la implementacin de una lista a travs de un arreglo?


a) Estructura de Datos Esttica
b) Estructura de Datos Dinmica

9) Cules de las siguientes operaciones sobre una lista pueden ser definidas usando
las operaciones primitivas nuevo e insertar?
a) esvacio
b) eliminar
c) encontrar
d) obtener

10) Para registrar los errores de un programa en C, se puede usar una estructura de
datos lista.
a) Verdadero
b) Falso

Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista


Libro 1: Estructura de Datos y Algoritmos 36

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Respuestas de la Unidad 1: Examen de Autoevaluacin


1) b
2) a
3) c
4) a
5) a
6) b
7) d
8) a
9) a, b, c y d
10) a

Libro 1: Estructura de Datos y Algoritmos


Unidad 1: Fundamentos de Estructura de Datos y Estructura de Datos Lista 37

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 2: Lista Enlazada


Objetivos de Aprendizaje
Al final de esta unidad, Usted ser capaz de:
Explicar la necesidad de listas enlazadas.
Describir las diferentes operaciones sobre una lista enlazada.
Discutir la implementacin de listas simplemente enlazadas.
Definir listas doblemente enlazadas y listas enlazadas circulares.
Comparar la implementacin de una lista usando arreglo y lista enlazada.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 39

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. Introduccin a Listas Enlazadas


En la Unidad 1: Estructura de Datos y Anlisis de Algoritmos, se discuti la estructura de
datos lista, su uso en aplicaciones y se realiz la implementacin usando un arreglo.
Tambin, se establecieron las limitaciones de la implementacin de una lista usando un
arreglo.

Hay otra implementacin de una estructura de datos lista llamada lista enlazada. Una
lista enlazada es una coleccin lineal de elementos de datos llamados nodos. Cada
nodo consiste de dos partes, la parte de la informacin y la parte de enlace, el cual
contiene un puntero al siguiente nodo.

Un ejemplo de un nodo tpico se muestra en la Figura 2.1.

Figura 2.1: Nodo en una Lista Enlazada

El nombre lista enlazada se deriva del hecho de que cada nodo en una lista provee un
enlace al siguiente nodo. El fin de la lista se indica por un valor NULL en lugar de un
puntero al siguiente nodo. Este valor NULL es tambin referido como un puntero null.

Esta implementacin permite expandir y contraer la lista durante el tiempo de ejecucin.


Esto es posible a travs de la ubicacin dinmica de memoria. Los elementos sucesivos
en una lista no necesariamente necesitan ocupar espacios contiguos en memoria, lo
cual hace la insercin y eliminacin de elementos de una lista relativamente simple.

La Figura 2.2 ilustra de una lista enlazada.

Figura 2.2: Una Lista Enlazada

Se observa en la Figura 2.2 que el puntero siguiente en el ltimo nodo de la lista es


NULL. Este valor NULL se usa en la mayora de operaciones de una lista enlazada para
detectar el final de la lista.

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 40

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Las listas se mantienen normalmente en un orden particular. El orden puede ser


ascendente o descendente para nmeros y orden lexicogrfico (alfabtico) para
cadenas (strings). En algunas otras instancias, la formacin de la lista enlazada puede
no seguir un orden en particular. En la Figura 2.2, el ordenamiento se basa en los
nombres de las ciudades, las cuales estn en orden alfabtico.

En esta figura, la parte de informacin de cada nodo tiene dos piezas de informacin, el
nombre de la persona y la ciudad en la que la persona reside. La parte de informacin
de un nodo, en una lista, puede ser un entero simple u otra lista en s. Por ejemplo, la
parte de informacin puede contener simplemente un entero denotando la edad de una
persona, o una lista denotando las calificaciones de estudiantes en diferentes cursos en
una universidad. Esta lista puede ser un arreglo u otra lista enlazada.

La lista en la Figura 2.2 tambin es referida como lista enlazada simple, ya que el
enlace de un nodo a otro es posible en una sola direccin.

Usualmente, cada nodo en una lista enlazada est representado por una estructura que
contiene dos o ms miembros, uno de ellos definitivamente es el puntero al siguiente
nodo en la estructura. Los otros miembros de la estructura almacenan informacin
basada en la aplicacin para la cual se utiliza la lista enlazada. A continuacin se dan
unos cuantos ejemplos de estructuras en C:

Ejemplo 1
typedef struct node {
int data;
struct node *next;
} Node_type;
Ejemplo 2
typedef struct node {
int studentid;
char studentname[30];
struct node *next;
} Node_type;
Ejemplo 3
typedef struct node {
char name[30];
char city[20];
struct node *next;
} Node_type;
En todos los ejemplos anteriores, se consigue un campo en la definicin de la estructura
que se refiere a la estructura en s, struct node *next. De aqu que las listas

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 41

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

enlazadas se llaman tambin estructuras auto-referenciadas. El Ejemplo 3 se refiere a la


lista enlazada presentada en la Figura 2.2.

En una lista enlazada donde el ltimo nodo se denota por un valor null en su campo
next es fcil seguir la pista hasta el final de la lista. Normalmente, se usa para
reconocer el inicio de la lista, un puntero externo a la lista referido como cabecera
(header). Ver Figura 2.2.

Inicializar la cabecera con NULL indica que la lista est vaca, como se muestra a
continuacin.
header = NULL;
Los nodos de cabecera se les referencia algunas veces como anclas (anchors). El valor
en la variable header cambia en las siguientes instancias:
Cuando el primer nodo se aade a la lista: Se asigna a la cabecera la ubicacin
de memoria del nuevo nodo adicionado.
Cuando un nuevo nodo va a ser insertado al inicio de la lista: Se le asigna a la
cabecera la ubicacin de memoria del nuevo nodo.
Cuando el primer nodo en la lista es eliminado: Se le asigna a la cabecera el
valor del nodo siguiente al primer nodo eliminado.
Cuando la lista contiene un solo nodo y el nodo es eliminado: Se le asigna a la
cabecera NULL.
La siguiente declaracin en C se usar para un nodo en una lista enlazada, con la
finalidad de mostrar las diferentes operaciones:

El cdigo en C empieza aqu


1. typedef int Element_type;
2. typedef struct LinkedList_node_tag {//Etiqueta del nodo
de lista
3. Element_type value;
4. struct LinkedList_node_tag *next;
5. } Node_type;
El cdigo C termina aqu

2. Operaciones en una Lista Enlazada


A continuacin, se entendern los usos de listas enlazadas al mostrar algunas de las
operaciones comunes.

2.1 Crear un Nuevo Nodo

La lista enlazada provee al programador la posibilidad de aadir nodos a la lista y


eliminar nodos de una lista dinmicamente. La creacin dinmica de nodos da la

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 42

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

posibilidad de expandir y contraer la lista programticamente mientras se est


ejecutando. Para aadir un nuevo nodo a la lista, el nodo tiene que haber sido creado
dinmicamente en memoria. Se puede hacer esto usando la funcin getNode(), el
cual toma un elemento y crea el nuevo nodo usando asignacin dinmica de memoria.

El cdigo en C empieza aqu


1. /* Obtener un nodo dinmicamente */
2. Node_type *getNode(Element_type elem) {
3. Node_type *node;
4. node = (Node_type *) malloc(sizeof(Node_type));
5. if (node!= NULL){
6. node->value = elem;
7. node->next = NULL;
8. }
9. return node;
10. }
El cdigo C termina aqu

La funcin getNode() es fcil de entender. Esta funcin hace lo siguiente:

Toma como entrada el elemento a ser aadido a la parte de informacin del


nodo.
Asigna memoria dinmicamente para un solo nodo usando la funcin malloc.
Asigna elem a la parte value del node.
Asigna NULL a la parte next del nodo.
Retorna el nuevo nodo recin creado en memoria.
La tarea de la funcin getNode() es slo crear un nuevo nodo. No se ocupa de la
insercin actual del nodo en la lista. Ver Figura 2.3.

Figura 2.3: Nuevo Nodo Creado en Memoria

Si la funcin getNode() se escribe como una funcin simple y autnoma, permitir


invocarla desde cualquier parte del programa que requiera la creacin de un nuevo
nodo para una lista enlazada, con una estructura de nodo similar.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 43

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

2.2 Recorrer la Lista Enlazada

El recorrido de una lista simplemente significa que se tiene que ir a travs de la lista,
visitando cada nodo en orden e imprimiendo la porcin de informacin de cada nodo.

El cdigo en C empieza aqu


1. /* El recorrido de una lista dada la cabecera */
2. void traverseList(Node_type *head) {
3. Node_type *ptr;
4. for (ptr = head; ptr != NULL; ptr = ptr->next)
5. printf("%d ",ptr->value);
6. printf("\n");
7. }
El cdigo C termina aqu

El recorrido es un algoritmo simple y directo. Esta funcin puede ser llamada en


cualquier momento, usando la cabeza de la lista como argumento. Perder la cabeza de
la lista har la lista inutilizable.

2.3 Insertar un Nodo Despus de un Nodo Dado

Un nodo puede ser insertado en la lista ya sea antes o despus de un nodo existente en
la lista.

Primero se discute el algoritmo para insertar un nodo despus de un nodo dado. Si


node es un puntero a otro nodo en la lista, entonces se inserta el nuevo nodo despus
del nodo apuntado por node. Asuma que el nuevo nodo con valor 299 debe ser
insertado despus del nodo con valor 210. Observe las Figuras 2.4 y 2.5 para ver como
se realiza la insercin.

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 44

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Figura 2.4: Insercin Antes de un Nuevo Nodo en la Lista

Figura 2.5: Insercin Despus de un Nuevo Nodo en la Lista

El cdigo en C para insertar un nuevo nodo despus de un nodo dado se proporciona a


continuacin.

El cdigo en C empieza aqu


1. /* Insertar un nodo despus de un nodo dado */
2. Node_type* insertAfter(Node_type *node, Element_type
elem) {
3. Node_type *ptr;
4.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 45

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5. if (node == NULL)
6. return NULL; /*No puede insertar*/
7. ptr = getNode(elem);
8. if (ptr != NULL) {
9. ptr->next = node->next;
10. node->next = ptr;
11. }
12. return ptr; /* Retorna el nuevo nodo creado
*/
13. }
El cdigo C termina aqu

La funcin insertAfter (insertarDespues) toma dos argumentos:


El nodo despus del cual el nuevo nodo ser insertado.
El elemento a ser aadido en el nuevo nodo.
Los cinco pasos que se seguirn para insertar un nodo despus de un nodo dado, son
los siguientes:

Paso 1: Primero se revisa si el nodo de entrada en la funcin, el cual tiene un valor


NULL. Un nodo no puede ser insertado despus de un nodo NULL. Entonces, se retorna
NULL a la funcin que invoca.

Paso 2: Si el nodo de entrada no es NULL, se crea un nuevo nodo usando la funcin


getNode(). La funcin getNode() retorna el nuevo nodo creado, el cual se almacena
en la variable ptr.

Se debe revisar si ptr == NULL antes de proceder. A ptr le ser asignado un valor
NULL cuando la funcin getNode() no es capaz de asignar memoria. Esto ocurre
cuando el sistema se queda sin memoria. Se ha incluido un if que revisa
cuidadosamente este problema. En la instancia del sistema que se queda sin memoria,
la funcin malloc retornar un valor NULL.

Paso 3: Si a ptr le es asignada la direccin del nuevo nodo, entonces se debe enlazar
a la lista. Esto se hace asignando el valor actual contenido en node->next en ptr-
>next. Al terminar esta operacin, la lista se ver como la Figura 2.6.

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 46

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Figura 2.6: Vista Intermedia de la Lista Enlazada

La vista presentada en la Figura 2.6 es una vista intermedia, cuando se encuentran


ambos ptr->next y node->next apuntando al mismo nodo. Esta vista representa el
estado entre las vistas mostradas en la Figura 2.4 y la Figura 2.5.

Paso 4: Para completar la insercin de un nuevo nodo, ahora se asigna a node->next


con el valor en ptr. Al hacer esto, se obtiene la lista ya mostrada en la Figura 2.5, una
lista con un nuevo nodo insertado despus de un nodo dado.

Paso 5: Se retorna el valor en ptr de regreso a la llamada de la funcin.


2.4 Insertar un Nodo Antes de un Nodo Dado

Una vez estudiado cmo insertar un nodo despus de un nodo dado, se discute a
continuacin cmo insertar un nodo antes de un nodo dado. Se ha visto que en una lista
enlazada simple, los punteros next siempre apuntan al siguiente nodo en la lista. Por lo
tanto, no hay manera de retroceder. Por esta razn, se necesita usar otra variable que
siempre est un paso atrs del nodo dado antes del cual el nodo debe ser insertado. Se
hacen las revisiones apropiadas al inicio de la funcin. El cdigo se presenta a
continuacin.

El cdigo en C empieza aqu


1. /* Inserta un nodo antes de un nodo dado */
2. Node_type* insertBefore(Node_type **head, Node_type
*node, \
3. Element_type elem) {
4. Node_type *ptr, *q;

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 47

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5. if (node == NULL)
6. return NULL;
7. if (head == NULL)
8. return NULL;
9. if (*head == NULL)
10. return NULL;
11.
12. ptr = getNode(elem);
13. if (ptr == NULL)
14. return NULL;
15. if (*head == node) {
16. ptr->next = *head;
17. *head = ptr;
18. }
19. else {
20. for (q = *head; q->next != node; q = q->next);
21. // Slo recorrido de la lista
22. ptr->next = q->next;
23. q->next = ptr;
24. }
25. return ptr; /* Retorna el nuevo nodo creado */
26. }
El cdigo C termina aqu

Ya que se necesita el puntero del nodo antes del nodo dado para que la insercin se
realice correctamente, la funcin insertBefore() (insertarAntes) toma el puntero de
la cabecera head como uno de los argumentos. El puntero de la cabecera de la lista es
pasado como un puntero a un puntero. Esto es porque cualquier cambio que afecte a la
cabeza de la lista en esta funcin, debe ser transmitido a la funcin que invoc.

Se declaran dos variables de puntero de Node_type, uno para obtener la direccin del
nuevo nodo y el otro para apuntar al nodo anterior al nodo dado. Despus de hacer
relevante las revisiones de los valores NULL, la funcin hace lo siguiente:
Si node y head son el mismo, entonces la insercin da lugar antes de la cabeza
de la lista y el nuevo nodo se convierte el primer nodo en la lista. Esto se hace
usando los dos siguientes pasos:
ptr->next = *head;
*head = ptr;

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 48

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Si node y head no son el mismo, entonces la insercin toma lugar antes de


node. Se recorre la lista usando head y se deja de recorrer cuando la variable
cumple la siguiente condicin:
q->next = node
Cuando esta condicin es verdadera, se tiene una variable que est un paso
detrs de node. Entonces se enlaza el nuevo nodo a la lista usando las
siguientes sentencias:
ptr->next = q->next;
q->next = ptr;
Finalmente, el valor en ptr es retornado a la funcin que invoca.
Un mtodo simple para insertar un nodo antes de un nodo dado, es realizar una
insercin despus de un nodo dado, luego intercambiar los contenidos de los dos nodos
node y ptr. Al intercambiar los contenidos de los dos nodos en la lista, se est
afectando la operacin de insercin antes del nodo dado. Este mtodo reduce el tiempo
de ejecucin del programa, ya que se evita el recorrido de la lista. Sin embargo, este
mtodo no funcionar cuando alguna otra variable en el programa est apuntando al
nodo cuyo contenido ha sido intercambiado con el nuevo nodo.

2.5 Eliminar un Nodo

Un nodo puede ser eliminado de tres maneras: eliminar el nodo actual, eliminar el nodo
previo o eliminar el siguiente nodo.

Si el nodo previo ha de ser eliminado, el nodo de cabecera y el nodo cuyo nodo previo
debe ser eliminado se requieren como argumentos.

Similarmente, la eliminacin del siguiente nodo requiere el nodo cabecera y el nodo


cuyo siguiente nodo debe ser eliminado, como argumentos. Claramente, en cualquier
funcin de eliminacin, el puntero del inicio de la lista es requerido. Usando este
puntero, la lista se recorre hasta donde la eliminacin debe realizarse. Escriba el cdigo
C para estas operaciones como ejercicios para entender mejor la eliminacin de una
lista enlazada.

El cdigo para eliminar el nodo actual se presenta a continuacin. Esta funcin requiere
head y el node a ser eliminado como argumentos. head apunta al primer nodo de la
lista.

El cdigo en C empieza aqu


1. /* Eliminar el nodo actual */
2. Node_type* deleteNode(Node_type *head, Node_type *node)
{
3. Node_type *ptr;
4. if (head == NULL || node == NULL)
5. return NULL;

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 49

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

6. if (head == node) {
7. head = node->next; // Primer nodo
8. free(node);
9. return head;
10. }
11. /* Moverse en la lista */
12. for (ptr = head; ptr->next != node; ptr = ptr->next);
13. ptr->next = node->next;
14. free(node);
15. return ptr; // Retorna el nodo previo al nodo de
entrada
16. }
El cdigo C termina aqu

Se hace la revisin de head==node cuando node y head son el mismo. En tal


situacin, head se modifica para apuntar al siguiente nodo de la lista. Se libera node
usando la funcin free. Se cambia head para apuntar a head->next antes de liberar
el nodo, ya que head y node son el mismo. Esto es un punto importante.

3. Encontrar el Predecesor y Sucesor en la Lista


Enlazada
En la Unidad 1: Estructura de Datos y Anlisis de Algoritmos se discuti la
implementacin de las funciones predecesor y sucesor para una lista usando arreglos.
Ahora, se implementan estas funciones para una lista usando la lista enlazada.

3.1 Predecesor de un Nodo en una Lista

La funcin predecesor toma como argumentos la cabecera de la lista y el nodo cuyo


predecesor debe ser encontrado. Retorna el nodo predecesor al nodo de entrada. La
funcin tambin realiza las revisiones apropiadas.

El cdigo en C empieza aqu


1. /* Encontrar el predecesor de un nodo en una lista */
2. Node_type *findPred(Node_type *head, Node_type *node) {
3. Node_type *ptr;
4.
5. /* Revisa por valores NULL de entrada */
6. if (head == NULL) { /* Error */
7. printf("\nPredecesor- Error de entrada: Head es
NULL\n");

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 50

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

8. return (NULL);
9. }
10. if (node == NULL) { /* Error */
11. printf("\nPredecesor- Error de entrada: Nodo es
NULL\n");
12. return (NULL);
13. }
14. else
15. if (node == head) {/* Si es primer nodo en lista
*/
16. printf("\nNo existe predecesor para el
primer \
17. nodo en la lista!\n");
18. return (NULL);
19. }
20. else
21. for (ptr = head; ptr->next && \
22. ptr->next != node; ptr = ptr-
>next);
23. if (ptr->next == NULL) {
24. printf("\nPredecesor- Error de entrada: Nodo de
entrada no \
25. se encuentra en la lista\n");
26. return (NULL);
27. }
28. else
29. return ptr;
30. }
El cdigo C termina aqu

Se revisa para asegurar que no se est trabajando con punteros NULL. Luego se realiza
una revisin para ver si el nodo de entrada es el mismo que head. De ser as, entonces
es el primer nodo en la lista y un mensaje apropiado se imprime. De no ser as, se
recorre la lista hasta que se est un paso anterior al nodo que es pasado como
argumento de la funcin.

El siguiente cdigo presenta otra versin de la funcin predecesor que toma un valor
como entrada en vez de un nodo.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 51

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

El cdigo en C empieza aqu


1. /* Encontrar el predecesor de un nodo en una lista,
dado un valor */
2. Node_type *findPredWithValue(Node_type *head, int
value) {
3. Node_type *ptr;
4.
5. /* Revisa por valores NULL de entrada */
6. if (head == NULL) { /* Error */
7. printf("\nPredecesor- Error de entrada: Head es
NULL\n");
8. return (NULL);
9. }
10. else
11. if (value == head->value) {
12. printf("\nNo existe predecesor para primer \
13. nodo en la lista!\n");
14. return (NULL);
15. }
16. else
17. // Recorre la lista para encontrar el nodo
18. // con el valor de entrada
19. for (ptr = head; ptr->next && \
20. ptr->next->value != value; ptr = ptr-
>next);
21.
22. if (ptr->next == NULL) {
23. printf("\nPredecesor- Error de entrada: Nodo de
entrada \
24. no se encuentra en la lista\n");
25. return (NULL);
26. }
27. else
28. return ptr;
29. }
El cdigo C termina aqu

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 52

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

3.2 El Sucesor de un Nodo en una Lista

La funcin de sucesor toma como argumentos la cabecera de una lista y el nodo cuyo
sucesor debe ser encontrado. Retorna el nodo sucesor al nodo de entrada. La funcin
realiza las revisiones apropiadas. En esta unidad se proporciona como ejemplo solo una
versin de la funcin sucesor, la que toma el nodo como entrada para encontrar el
sucesor. La otra versin se deja como ejercicio al estudiante, basado en la funcin
provista para predecesor.

El cdigo en C empieza aqu


1. /* Encontrar el sucesor de un nodo en una lista */
2. Node_type *findSucc(Node_type *head, Node_type *node) {
3. Node_type *ptr;
4. /* Revisa por valores NULL de entrada */
5. if (head == NULL) { /* Error */
6. printf("\nSucesor- Error de entrada: Head es
NULL\n");
7. return (NULL);
8. }
9. if (node == NULL) { /* Error */
10. printf("\nSucesor- Error de entrada: Nodo es
NULL\n");
11. return (NULL);
12. }
13. else {
14. for (ptr = head; ptr && ptr != node; ptr = ptr-
>next);
15. if (ptr) /* Nodo vlido en la lista */
16. if (node->next == NULL) {
17. printf("\nNo existe sucesor para ltimo nodo \
18. en la lista!\n");
19. return (NULL);
20. }
21. else
22. return node->next;
23. else {
24. printf("\nSucesor- Error de entrada: Nodo \
25. entrada no se encuentra en la lista\n");
26. return (NULL);
27. }

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 53

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

28. }
29. }
El cdigo C termina aqu

Se realizan las revisiones apropiadas al inicio de la funcin, adicionalmente se hace una


revisin para verificar si el nodo de entrada es el ltimo nodo de la lista. De ser as,
entonces se imprime un mensaje apropiado. Tambin, se asegura que node es un nodo
vlido en la lista, se recorre la lista empezando con head. Para entender como usar
estas funciones, se presenta la funcin main a continuacin con la salida de cada
segmento de cdigo. Note que hay valores que estn codificados en el programa. Se
pueden realizar los cambios apropiados para aceptar una entrada del usuario. Los
estudiantes pueden hacer esto como ejercicio.

El cdigo en C empieza aqu


1. int main() {
2. Node_type *head = NULL, *node1, *node2, *temp;
3. int value;
4. head = getNode(101);
5. printf("\nobtenerNodo: Creada una lista con valor
101!\n");
6. traverseList(head);
7. temp = insertBefore(NULL, head, 102);
8. if (temp)
9. head = temp;
10. else
11. printf("\ninsertarAntes: No pudo insertar 102
antes \
12. de 101 se pas un puntero NULL a la funcin!\n");
13. traverseList(head);
14. node1 = insertAfter(head,103);
15. printf("\ninsertarDespus: Insertado un nodo con 103 \
16. despes de 101\n");
17. traverseList(head);
18. insertBefore(&head, node1, 104);
19. printf("\ninsertarAntes: Insertado un nodo con 104 \
20. antes de 103\n");
21. traverseList(head);
22. node2 = insertAfter(head,145);
23. printf("\insertarDespus: Insertado un nodo con 145 \

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 54

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

24. despes de 101\n");


25. traverseList(head);
26. temp = head->next;
27. insertBefore(&temp, node1, 124);
28. printf("\ninsertarAntes: Insertado un nodo con 124 \
29. antes de 103\n");
30. traverseList(head);
31. insertAfter(node2,404);
32. printf("\n insertarDespus: Insertado un nodo con 404
\
33. despes de 145\n");
34. traverseList(head);
35. insertBefore(&head,head,105);
36. printf("\ninsertarDespus: Insertado un nodo con 105 \
37. despes de 101, nueva cabecera es
105\n");
38. traverseList(head);
39. insertBefore(&head,node1,105);
40. printf("\ninsertarAntes: Insertado un nodo con 105 \
41. antes de 103\n");
42. traverseList(head);
43. // Eliminar el primer nodo en la lista
44. head = deleteNode(head,head);
45. printf("\neliminarNodo: Eliminado nodo cabecera con
105, \
46. nueva cabecera es 101\n");
47. traverseList(head);
48. // Eliminar un nodo interno en la lista
49. deleteNode(head,node2);
50. printf("\neliminarNodo: Eliminado el nodo con 145\n");
51. traverseList(head);
52. // Eliminar el ltimo nodo de la lista
53. deleteNode(head,node1);
54. printf("\neliminarNodo: Eliminado el nodo con 103\n");
55. traverseList(head);
56. insertAfter(head,110);
57. printf("\ninsertarDespus: Insertado un nodo con 110 \
58. despes de 101\n");

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 55

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

59. traverseList(head);
60. node1 = head->next->next->next;
61. temp = findPred(head, node1);
62. if (temp)
63. printf("\nPredecesor de %d es %d\n", node1-
>value,\
64. temp->value);
65. node1 = head->next->next;
66. temp = findSucc(head, node1);
67. if (temp)
68. printf("\nSucesor de %d es %d\n", node1->value,\
69. temp->value);
70. value = 125;
71. temp = findPredWithValue(head, value);
72. if (temp)
73. printf("\nPredecesor de %d es %d\n", value, \
74. temp->value);
75. value = 124;
76. temp = findPredWithValue(head, value);
77. if (temp)
78. printf("\nPredecesor of %d es %d\n", value, \
79. temp->value);
80. return 1;
81. }
El cdigo C termina aqu

Se presenta un ejemplo de llamadas a las diferentes funciones de la lista enlazada para


mostrar su uso. La salida se da a continuacin:

Salida:
obtenerNodo: Creada una lista con valor 101!
101

insertarAntes: No pudo insertar 102 antes de 101 se pas


un puntero NULL a la funcin!
101

insertarDespus: Insertado un nodo con 103 despes de 101


101 103

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 56

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

insertarAntes: Insertado un nodo con 104 antes de 103


101 104 103

insertarDespus: Insertado un nodo con 145 despes de 101


101 145 104 103

insertarAntes: Insertado un nodo con 124 antes de 103


101 145 104 124 103

insertarDespus: Insertado un nodo con 404 despes de 145


101 145 404 104 124 103

insertarAntes: Insertado un nodo con 105 antes de 101,


nueva cabecera es 105
105 101 145 404 104 124 103

insertarAntes: Insertado un nodo con 105 antes de 103


105 101 145 404 104 124 105 103

eliminarNodo: Eliminado nodo cabecera con 105, nueva


cabecera es 101
101 145 404 104 124 105 103

eliminarNodo: Eliminado el nodo con 145


101 404 104 124 105 103

eliminarNodo: Eliminado el nodo con 145103


101 404 104 124 105

insertarDespus: Insertado un nodo con 110 despes de 101


101 110 404 104 124 105
Predecesor de 104 es 404

Succesor de 404 es 104

Predecesor- Error de entrada: Nodo de entrada no se


encuentra en la lista
Predecessor of 124 is 104
Una vez entendida la implementacin de una lista enlazada simple, a continuacin se
estudian otros dos tipos de listas enlazadas: la lista doblemente enlazada y la lista
enlazada circular.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 57

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

3.3 Lista Doblemente Enlazada

Una lista enlazada simple permite el recorrido slo en una direccin, es decir, desde la
cabecera y de acuerdo al orden dictado por los punteros. No es posible usar una lista
enlazada simple en una aplicacin que requiera ser recorrida al revs. Se ha visto
tambin, que en la lista simplemente enlazada, la insercin de un nuevo nodo antes de
otro nodo o la eliminacin del mismo presentan problemas. Esto se debe a que se
requiere mantener dos punteros y recorrer la lista en orden para realizar estas
operaciones.

En aplicaciones donde tales operaciones pesan mucho, la implementacin de lista


simplemente enlazada es tediosa. En tales casos, se puede usar otro tipo de lista
enlazada llamada lista doblemente enlazada.

Una lista doblemente enlazada tambin es una coleccin lineal de nodos, donde el nodo
consiste de lo siguiente:
Un campo de informacin.
Un puntero next, apuntando al siguiente nodo en la lista.
Un puntero prev, apuntando al nodo anterior en la lista.
Debido a que la lista doblemente enlazada tiene dos enlaces, uno al nodo previo y otro
al siguiente nodo, permite ser recorrida en ambos sentidos, adems de acceder al
predecesor y sucesor inmediato de un nodo dado.

La Figura 2.7 muestra un nodo en una lista doblemente enlazada y la Figura 2.8
muestra un ejemplo de una lista doblemente enlazada.

Figura 2.7: Nodo de una Lista Doblemente Enlazada

Figura 2.8: Lista Doblemente Enlazada

La declaracin en C para una lista doblemente enlazada se da a continuacin.

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 58

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

El cdigo en C empieza aqu


1. typedef struct DLinkedList_node_tag {
2. Element_type value;
3. struct DLinkedList_node_tag *next;
4. struct DLinkedList_node_tag *prev;
5. } Node_type;
El cdigo C termina aqu

De las Figuras 2.7 y 2.8 y la declaracin en C de la lista doblemente enlazada, es claro


que teniendo dos punteros para un nodo individual permite obtener el nodo previo sin
tener que recorrer la lista. Por ejemplo, si se tiene a ptr apuntando al nodo medio
teniendo el valor 145, como se muestra en la Figura 2.8, se puede obtener lo siguiente:
previousNode = ptr->prev;
nextNode = ptr->next;
As, las aplicaciones usan listas doblemente enlazadas cuando deben realizar un gran
nmero de operaciones de eliminacin e insercin.

3.4 Lista Enlazada Circular

Asuma que se est dando slo el ltimo nodo de una lista simplemente enlazada. No
hay manera de retroceder en la lista o ir a la cabeza de la lista.

La lista enlazada circular resuelve este problema. En una lista enlazada circular, el
ltimo nodo es conectado a la cabeza de la lista. En una lista enlazada circular, no hay
cabeza ni ltimo nodo y es posible moverse de un nodo a otro.

Un puntero externo al ltimo nodo en la lista permite tener un puntero a la cabeza de la


lista tambin, ya que el siguiente puntero del ltimo nodo apunta al primer nodo de la
lista.

En una lista enlazada no-circular, muchas operaciones requieren que la cabeza de la


lista sea pasada explcitamente como parmetros. Sin embargo, las operaciones de las
listas enlazadas circulares no requieren explcitamente que la cabecera se pase como
parmetro.

La Figura 2.9 es una ilustracin de una lista enlazada circular.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 59

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 2.9: Lista Enlazada Circular

En la Figura 2.9, el puntero next en el ltimo nodo en la lista est apuntando al primer
nodo en la lista. Tambin se encuentra que el nodo cabeza est apuntando al ltimo
nodo de la lista. Usando esto, se puede obtener el primer nodo de la lista como sigue:
firstNode = head->next;
Las listas enlazadas circulares son tiles en aplicaciones donde el recorrido entre los
nodos es frecuente. La estructura para una lista circular es la misma que para una lista
enlazada simple. Cuando el primer nodo en la lista se crea, el puntero next se apunta a
s mismo.
head = getNode(101);
head->next = head;
Slo se necesita recordar que head apunta al ltimo nodo en la lista y head->next al
primer nodo de la lista. El resto de las operaciones permanecen las mismas como en la
lista enlazada simple.

3.5 Aplicaciones que Usan Listas Enlazadas

En la Unidad 1: Estructura de Datos y Anlisis de Algoritmos, se listaron algunas reas


de aplicacin donde las listas enlazadas son tiles. Todos esos ejemplos pueden ser
implementados ya sea usando un arreglo o una lista enlazada. Depende de la aplicacin
la escogencia del mecanismo de implementacin. Algunos de estos puntos se
mencionan en la Tabla 2.1.

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 60

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Consideracin Implementacin de Lista Implementacin de Lista


Usando Arreglo Usando Lista Enlazada
Nmero de elementos Cuando se conoce el nmero Cuando no se conoce el nmero
en la lista (tamao) mximo de elementos que la lista mximo de elementos que la lista
tendr en todo momento. puede tener. Generalmente,
cuando la lista puede tener
pocos o muchos elementos.
Acceso arbitrario a Cuando hay la necesidad de Cuando el acceso a los
cualquier elemento en acceder a cualquier elemento en elementos es en el mismo orden
la lista la lista arbitrariamente con el en los cuales ellos son
mismo tiempo de acceso. actualizados o mantenidos de
inicio a fin.
Frecuencia de Cuando la frecuencia requerida Cuando el mecanismo usual de
Bsqueda es para buscar elementos acceso es solo secuencial. La
particulares, se puede usar bsqueda puede ser hecha
implementacin de arreglo con secuencialmente.
elementos ordenados lo que lo
hace excelente para
procedimientos de bsqueda
como bsqueda binaria.
Frecuencia de Cuando la necesidad de Cuando hay una necesidad
operaciones de insertar/eliminar un elemento definida de insertar/eliminar un
insercin y eliminacin particular en/desde una lista elemento particular en/desde una
ordenada sea requerido o no. En lista ordenada. En este caso,
este caso, se necesita mover los solo se necesita ajustar los
elementos en el arreglo del punto punteros de una lista enlazada
del elemento que es despus de la insercin/
insertado/eliminado. eliminacin.
Frecuencia de Comparativamente mejor que la Comparativamente mejor que un
ordenamiento lista enlazada cuando la lista arreglo cuando la lista no
requiere ser ordenada requiere de ordenamiento
frecuentemente. frecuente.
Orden de acceso al Preferido cuando se requiere de Preferido cuando se requiere el
elemento acceso aleatorio. acceso secuencial.
Tipo de elemento en la Cuando el tipo de elemento Puede usarse en ambos casos,
lista almacenado en la lista es un tipo esto es, que la lista de elementos
primitivo escalar. Es sean escalares y tipos de datos
extremadamente incmodo o casi de estructuras complejas.
imposible usarlo cuando los
elementos mismos son tipos de
datos de estructuras complejas
Unir dos listas Esta operacin usualmente no es Provee una funcin muy eficiente
posible. A lo ms, se puede tener para unir, ya que solo requiere
una de las listas en un arreglo de ajustar unos cuantos enlaces.
con suficiente espacio vaco para
contener a la otra lista.
Implementacin de una Cuando se tiene fijo el nmero de Cuando el nmero de elementos
lista FIFO elementos del mximo nmero crece o decrece arbitrariamente.
elementos.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 61

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Consideracin Implementacin de Lista Implementacin de Lista


Usando Arreglo Usando Lista Enlazada
Implementacin de una Muy eficiente cuando el tamao Es til cuando el tamao mximo
lista LIFO (pila) mximo de la lista se conoce por de la lista no se conoce. Las
adelantado. Las operaciones operaciones de push y pop son
como push,pop son fcilmente relativamente ineficientes.
implementadas.

Tcnica eficiente de Puede ser usado con cualquier Ninguna de las tcnicas de
ordenamiento tcnica de ordenamiento. Puede ordenamiento son eficientes.
usarse desde un ordenamiento Algunas tcnicas como merge
burbuja hasta un algoritmo sort o quicksort no estn
complejo como el quicksort. diseadas para ser usadas con
listas enlazadas.
Memoria Es empleada en aplicaciones que Se usa en aplicaciones que no
tienen restricciones de uso de tienen restricciones particulares
memoria. de uso de memoria y cuando la
memoria fsica es el nico lmite.
Tabla 2.1: Comparacin entre Arreglos y Listas Enlazadas

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 62

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Resumen
Ahora que ha completado esta unidad, Ud. debe ser capaz de:
Explicar la necesidad de las listas enlazadas.
Describir las diferentes operaciones sobre una lista enlazada.
Discutir la implementacin de una lista simplemente enlazada.
Definir la lista doblemente enlazada y lista enlazada circulares.
Comparar la implementacin de una lista usando arreglo y lista enlazada.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 63

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 2: Examen de Autoevaluacin


1) Una lista enlazada es una coleccin lineal de elementos de informacin llamados
____________
a) Items
b) Elementos
c) Nodos
d) Punteros

2) Cuntos punteros tiene un nodo en una lista de un slo sentido?


a) 0
b) 1
c) 2
d) Ninguna de las anteriores

3) Cul de los siguientes punteros indica el final de una lista?


a) Puntero Null
b) Puntero Invlido
c) Puntero de enlace
d) Ninguna de las anteriores

4) Las estructuras que tienen un elemento apuntando a una estructura en s son


estructuras auto-referenciadas.
a) Verdadero
b) Falso

5) La cabecera de una lista enlazada tambin se denomina __________


a) Base
b) Un ancla (anchor)
c) Un puntero null
d) Ambos a y b

6) Cul de los siguientes es una definicin correcta de un nodo en una lista


enlazada simple?
a) typedef struct LinkedList_node_tag {
int value;
struct LinkedList_node_tag *next;
} Node_type;

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 64

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

b) typedef struct LinkedList_node_tag {


int value;
struct LinkedList_node_tag next;
} Node_type;

c) typedef struct LinkedList_node_tag {


int value;
char type;
struct LinkedList_node_tag *next;
} Node_type;

d) typedef struct LinkedList_node_tag {


int type;
struct LinkedList_node tag *next1;
struct LinkedList_node_tag *next2;
} Node_type;

7) El algoritmo usado para insertar un nodo despus o antes de un nodo de entrada


es el mismo.
a) Verdadero
b) Falso

8) Se tiene una lista enlazada simple que tiene los siguientes elementos:
K H I L M O P
Si head apunta a K, Cul es el resultado de head->next->next->next?
a) H
b) L
c) O
d) Null

9) Cul de las siguientes listas enlazadas es ms til cuando la insercin antes de


un nodo dado es una operacin comn?
a) Simple
b) Circular
c) Doble
d) Todas las anteriores

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 65

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

10) Las aplicaciones de listas que requieren la insercin y eliminacin frecuente de


nodos sern mejores si se implementan con listas enlazadas.
a) Verdadero
b) Falso

Unidad 2: Lista Enlazada Libro 1: Estructura de Datos y Algoritmos 66

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Respuestas al la Unidad 2: Examen de Autoevaluacin


1) c
2) b
3) a
4) a
5) d
6) a, c y d
7) b
8) b
9) c
10) a

Libro 1: Estructura de Datos y Algoritmos Unidad 2: Lista Enlazada 67

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 3: Laboratorio de Listas


Enlazadas
Objetivos de Aprendizaje
Al final de esta unidad, usted ser capaz de:
Aplicar los conceptos de lista enlazada para resolver problemas.
Crear listas enlazadas.
Escribir operaciones en una implementacin de lista como lista enlazada.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Laboratorio de Listas Enlazadas 69

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejercicio de Laboratorio
Considere una lista enlazada que contiene enteros positivos.
Escribir:
Las funciones apropiadas para las operaciones en la lista enlazada.
Segmentos de programas para realizar los requerimientos especficos.
Un programa completo en C.
Tomando en cuenta las siguientes tareas:
1) Tomar tantos enteros positivos como sea posible como entrada y crear la lista
inicial hasta que el usuario ingrese el valor -9999 para terminar la entrada.
2) Imprimir la lista de la lista enlazada en el orden en que fueron ingresados.
3) Escribir una funcin llamada odd_print()que imprima slo los nmeros impares
en la lista.
4) Escribir una funcin llamada find_max()para encontrar el mximo entero en la
lista enlazada y que retorne el valor mximo.
5) Escribir una funcin llamada find_pos(x)que retorne la posicin de x en la lista
6) Mostrar el valor mximo en la lista y su posicin.

Tareas Opcionales:

Los siguientes dos ejercicios son opcionales:


7) Crear dos listas separadas que contengan slo los nmeros pares y los nmeros
impares respectivamente.
8) Unir las dos listas, de tal manera que la nueva lista resultante contenga todos los
nmeros pares antes que todos los nmeros impares e imprimir la nueva lista.
Recomendaciones:
Crear una lista enlazada con entradas de un usuario.
El final de entrada se puede indicar por 9999.
Asegurar que 9999 no sea parte de la lista.
Revisar la validez de entrada. No aceptar nmeros enteros negativos.
Si 9999 es el nico valor ingresado entonces la lista es una lista vaca. El resto
del programa debe funcionar de acuerdo a esto. No se puede encontrar el
mximo de una lista vaca.
Para cada pregunta del ejercicio, escribir funciones separadas.
Hacer el programa tan modular como sea posible.

Unidad 3: Laboratorio de Listas Enlazadas Libro 1: Estructura de Datos y Algoritmos 70

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Recomendaciones para las Tareas Opcionales:


Crear dos listas diferentes para los enteros pares y los enteros impares.
Cuando se crea la lista de impares, no permitir pares como entrada. Mostrar los
mensajes apropiados.
Cuando se crea la lista de pares, no permitir impares como entrada. Mostrar los
mensajes apropiados.
El final de la entrada de estas dos listas es tambin -9999.
Si slo -9999 se ingresa en ambas listas, entonces no hay nada para unir.
Si -9999 es entrada para una de las dos listas, entonces la lista unida contiene la
otra lista no vaca.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Laboratorio de Listas Enlazadas 71

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 4: Pila
Objetivos de Aprendizaje
Al final de esta unidad, Usted ser capaz de:
Definir la estructura de datos de pila.
Explicar las diferentes operaciones definidas en una pila.
Describir las operaciones del TDA Pila.
Explicar la implementacin de una pila usando un arreglo y una lista enlazada.
Discutir el uso de las pilas en la resolucin de problemas.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 73

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. Pilas
Las listas y los arreglos permiten que un elemento sea insertado o eliminado de
cualquier lugar arbitrario dentro de la estructura. Sin embargo, hay muchas situaciones
que requieren que los elementos se inserten y eliminen slo del comienzo o el final de la
lista. Una pila es una de las estructuras de datos, que permite que los elementos sean
aadidos o eliminados slo por un lado. Las pilas son comunes en la vida real; se tienen
pila de platos, pila de servilletas, pila de libros, pila de dlares, pila de peridicos. Ver
Figura 4.1.

Figura 4.1: Ejemplo de Pilas

El final donde los elementos son aadidos o eliminados se conoce como tope (top) de
la pila. En una pila, los elementos que son aadidos de ltimos son los primeros en ser
removidos. De aqu que, las pilas tambin son conocidas como listas ltimo en Entrar,
Primero en Salir (LIFO siglas en ingls).

La Figura 4.2 muestra un ejemplo de insercin y eliminacin en la misma pila.

Figura 4.2: Ejemplo Mostrando Insercin y Eliminacin en una Pila

En una pila, la operacin de insercin se refiere como push y la operacin de


eliminacin se refiere como pop. De aqu que las pilas tambin son conocidas como
pilas de empuje hacia abajo (Pushdowns list).

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 74

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

2. Tipo de Dato Abstracto Pila


Las pilas pueden ser definidas como TDA de acuerdo a:
new(S): Crea una nueva pila S. La pila S est vaca cuando se crea.
push(S, element): Pone un elemento en el tope de la pila.
pop(S): Elimina el elemento del tope de la pila.
top(S): Retorna el elemento en el tope de la pila.
isempty(S): Retorna verdadero si es vaca, de lo contrario retorna falso.
En la definicin anterior de las operaciones en una pila, S se refiere a la pila.

Las dos operaciones primitivas de una pila, new y push ayudan en la definicin de las
otras operaciones. Matemticamente, todas las otras operaciones de pila pueden ser
definidas en trminos de estas dos operaciones primitivas.

La operacin new toma S como argumento, mientras que la operacin push toma los
argumentos S y element.

Habiendo discutido las operaciones a nivel TDA para la pila, se define a continuacin la
operacin pop usando las dos operaciones primitivas.

2.1 Definir pop usando new y push

La operacin pop(new) siempre produce un error si no hay elementos en una nueva


pila. Esto se escribe como sigue:
pop(new) = error
Un elemento no se puede quitar de una pila vaca. As, cuando se define pop(new) se
genera un error.

Ahora, considere push(S,element) para una pila S donde S no es una pila nueva, si
lo fuera, colocar (push) element dentro de ella la hace no-vaca. Por lo tanto, sacar
(pop) del tope de la pila S que tiene element colocado en ella, debe dar pila vaca.
element puede ser removido usando la operacin pop de la siguiente manera:
pop(push(S,element)) = S
pop(push(S,element)) da como resultado S dado que el ltimo elemento insertado en
S (ej. element) es el que se quita. Notar que esto explica la operacin claramente sin
tener que entrar en especificaciones de la implementacin.

Para explicar las tres operaciones, llamadas pop, isempty y top, se usa la pila
llamada myStack.

Ejemplo para ilustrar pop usando new

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 75

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ahora, se crea una nueva pila llamada myStack. Observe que cuando una pila es
creada usando la operacin new slo se crea una pila vaca

myStack es una pila vaca, no tiene elementos

Pasando esta nueva pila a pop generar un error, ya que no se puede sacar nada de
una pila vaca.

Ejemplo para ilustrar pop usando push en una Pila Vaca

Asuma que un entero 200 es ingresado en la pila vaca myStack.


push(myStack,200)retornar myStack con slo un elemento 200 insertado en l.

Ahora si la pila no-vaca myStack se pasa como argumento a pop, la operacin pop
elimina el tope de la pila, la cual en esta instancia es 200, ya que es el nico elemento
en la pila. Con la extraccin (pop) del nuevo elemento insertado 200, el estado de la pila
vuelve a ser el anterior, la pila vaca.

Ejemplo para ilustrar pop usando push en una Pila No-Vaca

Ahora, asuma que myStack no est vaca y tiene los siguientes elementos:
100 105 240 210
210 es el elemento tope. Sin embargo, push(myStack, 200) retornar myStack con
200 como elemento tope. Cuando esta nueva pila myStack se pasa a la operacin pop,
remueve 200, retorna una pila con los siguientes elementos:
100 105 240 210
Esta pila es la misma que fue pasada como argumento a push. El estado de myStack
vuelve a ser el estado anterior, una pila con cuatro elementos.

Se dice entonces que:


pop(push(S,element)) = S
Se termina con la pila original al final de la operacin pop en push.

2.2 Definir top Usando new y push

Una pila new no contiene elementos y por lo tanto, el elemento top no existe o no est
definido. top(new) es un error ya que no existe elemento que retorne el valor tope.
Esto se escribe de la siguiente manera:
top(new) = error
Considere la pila que resulta de push(S,element). Colocando (push) element en la
pila S significa que element se convierte en el top de la pila. As que para obtener top
de la pila, en este caso se hace lo siguiente:

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 76

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

top(push(S,element)) = element
La operacin anterior implica que el elemento element se inserta en el top de la pila.

Ejemplo para ilustrar top usando new

Considere de nuevo el ejemplo de myStack. Cuando myStack est vaca, top retorna
un error ya que una lista vaca no puede tener ningn elemento.
top(new) = error
Ejemplo para ilustrar top usando push en una Pila Vaca

Si myStack est vaca, entonces el colocar (push) el elemento 200 en myStack resulta
en que myStack tiene slo el elemento 200. Cuando myStack con 200 se pasa a top,
sta retorna 200 que es el elemento element colocado (push) de ltimo en myStack.

Ejemplo para ilustrar top usando push en una Pila No-Vaca

Si myStack inicialmente tiene 100, 105, 240 y 210, se realiza push(myStack, 200),
donde 200 es el elemento, los elementos en la pila despus de colocarlos son:
100 105 240 210 200
200 ser el tope de la pila. Cuando esta nueva myStack se pase a la operacin top,
retornar 200, que fue el ltimo elemento element insertado (push) en myStack.

De aqu que, para pilas vacas y no-vacas


top(push(S,element)) = element
Ambas operaciones push y top resaltan la esencia de una pila, llamada como concepto
Ultimo en Entrar, Primero en Salir (Last-In First-Out). En ambos casos, la operacin es
sobre el elemento tope de la pila.

2.3 Definir isempty usando new y push

Una pila new es vaca. Para declarar esto, se escribe:


isempty(new) = true
push(S,element) resulta en una pila no vaca, an cuando S estuvo vaca antes. Por lo
tanto, cuando se hace isempty a push(S,element)el resultado debe ser falso. Se
escribe esto de la siguiente manera:
isempty(push(S,element)) = false

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 77

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejemplo para ilustrar isempty usando new

Tomando el mismo ejemplo de myStack, se puede ver que una nueva pila es vaca, as
resulta en un valor verdadero la operacin isempty.
Para definir isempty en push, se observa ambas condiciones, myStack siendo vaca
y no-vaca.

Ejemplo para ilustrar isempty usando push en una Pila Vaca

Cuando myStack es vaca, aadir un elemento 200 lo hace no-vaca. Esta pila no-vaca
se pasa a la operacin isempty, la cual retorna false.

Ejemplo para ilustrar isempty usando push en una Pila No-Vaca

En una pila no-vaca, aadir otro elemento no altera el estado de la pila. De aqu que
isempty retorna false.
Por lo tanto, basado en el razonamiento anterior para pop, top e isempty, se pueden
escribir reglas para las operaciones de pila como sigue:
Para todo S y element, lo siguiente ser vlido:
pop(new) = error
pop(push(S,element)) = S
top(new) = error
top(push(S, element)) = element
isempty (new) = true
isempty (push(S, element)) = false
Las reglas de las operaciones pop, top e isempty se declaran en trminos de los
operadores primitivos new y push. Estas reglas se denominan axiomas.

3. Implementar Pilas Usando Arreglos


Las pilas pueden ser implementadas usando un arreglo. Si se usan los arreglos, el
nmero de elementos en la pila debe ser definido al tener un mximo fijo, tal como
STACKMAX. La pila tambin debe ser definida para contener elementos de un tipo
particular, por ejemplo: entero, real, arreglos o estructuras. Se declara a continuacin
una pila general con un Element_type que describe el dato que ser colocado en la
pila.

El cdigo en C empieza aqu


1. #define STACKMAX 100
2. #include stdio.h
3. #include stdlib.h
4. typedef int Element_type;

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 78

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

5.
6. // definicin de pila
7. // Contiene top que referencia el elemento top
8. // Contiene una pila de arreglo
9. typedef struct stacker {
10. int top;
11. Element_type stack[STACKMAX];
12. } Stack_type;
El cdigo C termina aqu

Si se quiere una pila de caracteres, se debe slo cambiar el typedef de


Element_type de acuerdo a esto. La ventaja de crear un tipo Element_type es que
permite cambiar el tipo de dato de int a char en un slo lugar, en el punto donde se
define Element_type. La mayora de las funciones de pila usan Element_type, ya
sea como argumento o como variable local. El cambio hecho a nivel de la definicin de
tipo, automticamente se refleja donde el Element_type se usa.

La funcin prototipo para implementar la pila usando arreglos se da a continuacin.

El cdigo en C empieza aqu


// La funcin prototipo para las operaciones de pila
void newStack(Stack_type *stack);
void push(Stack_type *st_ptr, Element_type elem);
Element_type pop(Stack_type *st_ptr);
Element_type top(Stack_type *st_ptr);
int isEmpty(Stack_type *st_ptr);
int isFull(Stack_type *st_ptr);
El cdigo C termina aqu

A continuacin se discute la implementacin de las operaciones en una pila. Se


continuar con la descripcin de las operaciones de una pila como se da en un TDA,
excepto para el caso de la operacin pop. El TDA describi a pop como eliminar el
elemento tope de la pila. Haba una operacin separada top para retornar el elemento
del tope de la pila, sin eliminarlo. Aqu pop eliminar el tope de la pila y retornar el
valor del elemento eliminado. Esta definicin de pop es muy til en aplicaciones que
usan una pila.

La Operacin new y push

El cdigo en C empieza aqu


1. /* New inicializa la pila al estado vaco */

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 79

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

2. void newStack(Stack_type *st_ptr) {


3. st_ptr->top = 0;
4. }
5. /* La Operacin Push */
6. void push(Stack_type *st_ptr, Element_type elem){
7. if(st_ptr == NULL)
8. return;
9. if (isFull(st_ptr))
10. return;
11. else {
12. st_ptr->stack[st_ptr->top++]= elem;
13. return;
14. }
15. }
El cdigo C termina aqu

En la operacin push, se revisa si hay un espacio en la pila. Si hay espacio, se inserta


el elemento en el tope de la pila y se incrementa el puntero de la pila. De lo contrario,
slo retorna la funcin.

La Operacin pop

El cdigo en C empieza aqu


1. /* La Operacin Pop */
2. Element_type pop(Stack_type *st_ptr) {
3. if (isEmpty(st_ptr))
4. return -1;
5. else
6. return st_ptr->stack[--st_ptr->top];
7. }
El cdigo C termina aqu

Note que el tope de la pila se decrementa antes de retornar el valor. Al momento de la


creacin, top se coloca en 0. Cuando se agrega el primer elemento, se aade en la
posicin 0, luego top se coloca en 1. En cualquier momento, top es la posicin donde
se puede aadir un elemento. Antes de quitar un elemento de la pila, debe realizarse
una revisin para ver si la pila de donde se intenta quitar el elemento est vaca. En la
operacin pop, el elemento tope de la pila retorna como resultado. Esta es una pequea
variacin de la operacin en el TDA. Muchas implementaciones de la operacin pop
retornan el resultado cuando se elimina de la pila.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 80

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

La Operacin top

El cdigo en C empieza aqu


1. /* La Operacin Top */
2. Element_type top(Stack_type *st_ptr) {
3. if (isEmpty(st_ptr))
4. return -1;
5. else
6. return st_ptr->stack[st_ptr->top-1];
7. }
El cdigo C termina aqu

No se est decrementando top pero slo retornando el valor de top-1. Esta operacin
es similar a la operacin pop. Sin embargo, retorna el elemento top de la pila sin
eliminarlo de la pila. Tambin note que st_ptr->top no cambia.

Las Operaciones isEmpty e isFull

El cdigo en C empieza aqu


1. /* Para ver si la pila es vaca */
2. int isEmpty(Stack_type *st_ptr) {
3. if(st_ptr == NULL)
4. return (1);
5. if(st_ptr->top == 0)
6. return (-1);
7. else
8. return (0);
9. }
10.
11. /* Para ver si la pila esta llena */
12. int isFull(Stack_type *st_ptr) {
13. if(st_ptr == NULL)
14. return (-1);
15. if(st_ptr->top == STACKMAX)
16. return (1);
17. else
18. return (0);
19. }

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 81

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

El cdigo C termina aqu

En el TDA, no se defini la operacin lleno (full). Tericamente hablando, una pila


nunca est llena. Pero cuando se implementa, hay limitaciones, tales como el tamao
del arreglo definido para la pila. De aqu que una funcin llamada isFull() sea
necesaria.

Hay varias ventajas para usar funciones separadas para implementar las diferentes
operaciones sobre las pilas. En la implementacin de pilas usando arreglos, la
naturaleza de las operaciones es simple. Sin embargo, se desea declarar y usar una
estructura para una pila, adems de tener funciones separadas para implementar las
operaciones. Esto es porque, en un problema grande, es mejor tenerlas como
funciones, en lugar de repetir cdigo por todos lados. Suponga que se consigue una
mejor implementacin (que arreglos), el cambio se localizar slo en estas funciones. El
uso de nombres de funciones tales como push, pop o top harn el programa ms
legible. La separacin de estructuras de datos de su implementacin tambin ayuda a
un diseo top-down.

Para revisar si estas funciones estn implementadas correctamente, se puede escribir la


siguiente funcin main.

El cdigo en C empieza aqu


1. // Funcin Main
2. int main() {
3. Stack_type *sptr;
4. int element;
5. sptr = (Stack_type *) malloc(sizeof(Stack_type));
6. // Inicializar la pila
7. newStack(sptr);
8. printf("Ingrese nmeros a la pila, finalice con -
9999:\n");
9. scanf("%d", &element);
10. if (element == -9999)
11. return 1;
12. else {
13. do {
14. push(sptr, element);
15. scanf("%d", &element);
16. } while (element != -9999);
17. printf("\n");
18. }
19. printf("\nPila completamente llena con nmeros!\n");

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 82

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

20. printf("\nEl elemento tope es: %d\n", top(sptr));


21. /* Saca todos los elementos de la pila */
22. while (!isEmpty(sptr)) {
23. printf("\nElementos sacados (popped) de la pila
son:\n");
24. printf("%d\n", pop(sptr));
25. }
26. if (isEmpty(sptr))
27. printf("\nLa pila est vaca!\n");
28. return 1;
29. }
El cdigo C termina aqu

La funcin main toma la entrada del usuario y la coloca en la pila. Luego imprime el
elemento tope de la pila y quita todos los elementos de la pila. Por lo tanto, la pila estar
vaca al final de la funcin main. Se ha definido STACKMAX a 100. Si STACKMAX es
reducido a cinco, el programa ignora las entradas despus de los primeros cinco
nmeros. Esto se toma en cuenta en la funcin push, donde se aade a la pila slo si no
est llena. A continuacin se da la entrada y salida del programa.

Entrada:
Ingrese nmeros a la pila, finalice con -9999:
-1
0
-100
201
345
10003
89
-76
-9999
Salida:
Pila completamente llena con nmeros!
El elemento tope es: -76

Elementos sacados (popped) de la pila son:


-76

Elementos sacados (popped) de la pila son:

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 83

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

89

Elementos sacados (popped) de la pila son:


10003

Elementos sacados (popped) de la pila son:


345

Elementos sacados (popped) de la pila son:


201

Elementos sacados (popped) de la pila son:


-100

Elementos sacados (popped) de la pila son:


0

Elementos sacados (popped) de la pila son:


-1
La pila est vaca!
A continuacin se presenta una aplicacin simple para ilustrar como se pueden usar las
pilas.

Ejemplo 4.1

Asuma que se necesita aceptar una lnea de caracteres como entrada e imprimirlos en
orden invertido. Para lograr esto, los caracteres se leen como entrada y se colocan en la
pila. Luego se quitan de la pila. Salen en orden invertido e impresos en ese orden.

Anteriormente se tena el tipo definido Element_type para ser tipo int. Para esta
funcin se necesita cambiar Element_type a:
typedef char Element_type;
El cdigo en C empieza aqu
1. void reverseAndPrint() {
2. Element_type elem;
3. /* Una pila para contener los caracteres de entrada */
4. Stack_type myStack;
5.
6. /* Crear una pila vacia */
7. newStack(&myStack);

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 84

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

8.
9. /* Ingreso */
10. printf("Ingrese la cadena a invertir:\n");
11. /* Bucle para tomar la entrada y colocar cada carcter
en la
12. pila */
13. scanf("%c", &elem); // Primer carcter
14. while (elem != '\n') {
15. /* Colocar el carcter en la pila */
16. push(&myStack, elem); // Siguiente carcter
17. scanf("%c", &elem);
18. }
19. /* En este punto los caracteres estn en la pila */
20.
21. /* Imprimir la cadena en orden inverso */
22. printf("\nLa cadena invertida es:\n");
23. /* Bucle para sacar elementos de la pila */
24. /* mientras la pila no este vacia */
25. while (!isEmpty(&myStack)) {
26. /* Quitar el elemento tope de la pila */
27. elem = pop(&myStack);
28. /* Imprimir el valor del elemento */
29. printf("%c",(char) elem);
30. }
31. /* Imprime una nueva lnea al final */
32. printf("\n");
33. }
El cdigo C termina aqu

Usando las funciones de pila, se implementa reverseAndPrint() como una funcin


independiente (standalone). Se crea una nueva pila, se colocan (push) los caracteres de
la cadena de entrada en la pila y finalmente se sacan (pop). Del concepto de
almacenamiento LIFO se obtiene la cadena invertida cuando se saca cada elemento de
la pila.

Suponga que el texto PHANTOM es la entrada y se debe tener la salida como MOTNAHP.
Si la entrada es MADAM entonces la salida debe ser MADAM. Si se invoca a
reverseAndPrint() desde main, se obtiene un mensaje de ingresar una cadena. La
cadena invertida se muestra de nuevo con el mensaje que se muestra a continuacin.

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 85

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ingrese la cadena a invertir:


Data Structures and Algorithms

La cadena invertida es:


smhtiroglA dna serutcurtS ataD

Final del Ejemplo 4.1

Una vez aprendido cmo implementar una pila usando un arreglo, se discute cmo
implementar pilas usando listas enlazadas.

4. Pila como Lista Enlazada


Las pilas tambin pueden ser implementadas usando listas enlazadas. En una lista
enlazada, cada elemento se almacena en un nodo y todos los nodos estn conectados.
Recuerde la definicin de nodo de lista enlazada:
typedef int Element_type;

// Definir un nodo
typedef struct node {
Element_type info;
struct node *next;
} Node_type;
Una pila es un tipo especial de lista, en la que slo un lado es considerado visible.
Todas las operaciones ocurren en este lado final visible. Cuando se usan listas
enlazadas como mtodo de implementacin, se debe saber si el final o el comienzo de
la lista que representa el tope de la pila.

En una lista enlazada simple no se puede retroceder, si el final de la lista se le considera


el tope de la pila, habr problemas para la operacin pop. Cada vez que una operacin
pop sea realizada, la lista entera debe recorrerse para encontrar el tope de la pila. Por lo
tanto, el comienzo de la lista siempre se usa como tope de la pila. Ya se ha visto la
necesidad y uso del nodo cabecera en una lista enlazada simple. El nodo cabecera
representa el tope de una pila implementada usando lista enlazada.

Una vez que se tiene top, se sabe como hay que moverse al primer elemento de una
lista enlazada, la cual tambin es el tope de la pila. Despus de eso, acceder a todos los
elementos de la pila es directo.

Se declara una estructura para mantener una pila como sigue:


// Definir el tope de la pila
typedef struct stacker {
Node_type *top;

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 86

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

} Stack_type;
Los prototipos de las funciones de pila se dan a continuacin.

El cdigo en C empieza aqu


Node_type *createNode(Element_type);
void newStack(Stack_type *);
int isEmpty(Stack_type *);
Element_type top(Stack_type *);
void push(Stack_type *, Element_type);
Element_type pop(Stack_type *);
El cdigo C termina aqu

Seguidamente, se presenta la implementacin de cada funcin de pila.

El cdigo en C empieza aqu


1. /* Crear un nuevo nodo */
2. Node_type *createNode(Element_type element) {
3. Node_type *node;
4. node = (Node_type *) malloc(sizeof(Node_type));
5. node->info = element;
6. node->next = NULL;
7. return node;
8. }
9. /* Crear una pila nueva */
10. void newStack(Stack_type *st_ptr) {
11. st_ptr->top = NULL;
12. }
13. /* Determinar si la pila est vacia */
14. int isEmpty(Stack_type *st_ptr) {
15. if (st_ptr->top == NULL)
16. return 1;
17. else
18. return 0;
19. }
20. /* Obtener el elemento en el frente de la pila */
21. Element_type top(Stack_type *st_ptr) {
22. if (!isEmpty(st_ptr))

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 87

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

23. return (st_ptr->top->info);


24. else
25. /* Retorna -1 cuando la pila es vacia */
26. return (-1);
27. }
28. /* Adicionar un elemento a la pila */
29. void push(Stack_type *st_ptr, Element_type element) {
30. Node_type *node;
31. if(st_ptr == NULL)
32. return;
33. node = createNode(element);
34. if (st_ptr->top == NULL)
35. st_ptr->top = node;
36. else {
37. node->next = st_ptr->top;
38. st_ptr->top = node;
39. }
40. }
41. /* Eliminar un elemento de la pila */
42. Element_type pop(Stack_type *st_ptr) {
43. Node_type *q;
44. Element_type element;
45. if(st_ptr == NULL)
46. return -1;
47. if (isEmpty(st_ptr))
48. /* Retornar -1 cuando la pila est vacia y no se puede
eliminar */
49. return -1;
50. q = st_ptr->top;
51. element = q->info;
52. st_ptr->top = q->next;
53. free(q);
54. return element;
55. }
El cdigo C termina aqu

Cuando se colocan elementos en la pila, el nuevo nodo (elemento tope) se aade al


frente de la pila, haciendo que top apunte al nuevo nodo.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 88

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

La funcin main escrita para la implementacin del arreglo se puede usar para la
implementacin de la lista enlazada, casi sin cambios.

5. Aplicaciones de Pilas
Hay un nmero de aplicaciones que requieren la pila como estructura de datos. Se
presenta a continuacin una lista de dichas aplicaciones en orden creciente de
complejidad.

5.1 Procesamiento de Cadenas

Hay muchas aplicaciones de procesamiento de cadenas (string) donde las pilas son
estructuras de datos vitales. Un ejemplo simple es la deteccin de cadenas palndrome.
Una cadena es palndrome (o un nmero) cuando los caracteres individuales se leen
igual en ambas direcciones.

5.2 Balanceo de Parntesis en Expresiones Aritmticas

Cuando los programas son escritos en un lenguaje de alto-nivel como C o C++, se hace
uso de las expresiones aritmticas. Estas expresiones aritmticas usan parntesis. Una
de las funciones importantes del anlisis sintctico es revisar si los parntesis estn
balanceados en las expresiones aritmticas. En otras palabras, se debe revisar si los
parntesis izquierdos y los parntesis derechos concuerdan en nmero y tambin en la
forma de anidarlos. Se puede emplear una pila para realizar esta revisin.

5.3 Convertir una Expresin de Infija a Postfija

Cuando las expresiones aritmticas se escriben en lenguajes de alto nivel como C o


C++, se usa la notacin infija. Pero se puede realizar la evaluacin de las expresiones
aritmticas ms fcilmente si la expresin se convierte a notacin postfija. Una pila se
usa para convertir una expresin en la notacin infija a postfija.

5.4 Evaluar una Expresin Postfija

Una expresin aritmtica que ha sido convertida a notacin postfija se puede evaluar
fcilmente usando una pila.

5.5 Soporte a los Mecanismo de Llamada y Retorno de Funcin o


Procedimiento.

Cuando una funcin se invoca, los parmetros deben ser estar disponibles para el
programa que invoca. Despus de que la ejecucin de la funcin se completa, el control
debe retornar a la sentencia siguiente a la invocacin de esa funcin. Esto requiere
hacer disponible los parmetros a la funcin llamada y mantener el estado del progreso
(incluyendo direccin de retorno). Las pilas son las estructuras de datos que
principalmente se usan para soportar el mecanismo de llamada y retorno de una funcin
o procedimiento.

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 89

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5.6 Soporte para la Recursin

Aparte de proveer soporte para el mecanismo de llamada y retorno de una funcin o


procedimiento, las pilas juegan un rol importante para implementar la recursin.

5.7 Soporte para la Estrategia de Rastreo

Hay muchas aplicaciones, incluyendo juegos que requieren estrategias de rastreo


(backtracking strategy). Como un ejemplo, considere un laberinto a travs de la cual hay
que moverse. Una de las estrategias ser seguir el camino hasta llegar al final,
retroceder al paso previo y luego proceder. El rastreo requiere almacenar todos los
movimientos y estados previos y tener la capacidad de retroceder al movimiento y
estado previo. Una pila es una estructura de datos ideal para estas situaciones.

5.8 Aplicacin de Pilas: Un Ejemplo

A continuacin se aprender el uso de las pilas en una aplicacin. Uno de los usos ms
comunes y significativos de una pila es evaluar expresiones aritmticas. Una expresin
aritmtica se representa de la siguiente forma:
a + b c * d + e / f
Una expresin aritmtica simple a+b puede ser fcilmente evaluada, ya que slo hay
dos operandos y un operador. Pero a medida que se agregan ms operandos y
operadores a la expresin, se hace ms difcil evaluarla programticamente. La
dificultad se da no slo por el nmero de operandos y operadores, sino tambin debido
a la precedencia de operadores. Por ejemplo, sea la siguiente expresin aritmtica:
a * b (c + d) * (e f)
Se sabe que las expresiones entre parntesis c+d y e-f se evalan antes que el resto
de los operadores aplicados a los operandos. As, es necesario recordar los resultados
de c+d y e-f cuando la expresin completa se evala. La evaluacin lgica entera se
vuelve cada vez ms complicada.

Las expresiones se usan normalmente en la forma llamada infija. Para dar una solucin
a la evaluacin de expresiones programticamente, estas expresiones infijas se
convierten al formato postfijo. El nombre infija viene porque los operadores se colocan
entre los operandos. En una operacin postfija, los operadores siguen a los operandos a
los cuales aplican.

Una expresin en forma infija tambin puede ser convertida en forma prefija. En este
caso, los operadores vienen antes de los operandos. La notacin prefija slo se
menciona para completar el concepto. Una discusin del tema va ms all del alcance
de este curso.

A continuacin se presentan algunos ejemplos para entender las diferencias entre las
tres formas.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 90

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Ejemplo 1
infijo - a + b
postfijo - a b +
prefijo - + a b
En la forma postfija se tiene al operador + despus de los operandos a y b.

Ejemplo 2
infijo - a + b c
postfijo - a b + c
prefijo - - + a b c
En la expresin anterior, el operador con menor precedencia es -. a+b se evala antes y
el resultado de a+b se usa en la operacin de substraccin.

Ejemplo 3
infijo - a + b * c
postfijo - a b c * +
prefijo - + a * b c
En esta expresin el operador con menor precedencia es el +, el cual ser usado sobre
a y el resultado de b*c. As, se observa al final de la forma postfija y al inicio de la
forma prefija.

Ejemplo 4
infijo - a + b * (c d)
postfijo - a b c d - * +
prefijo - + a * b c d
En esta expresin se han introducido parntesis. El orden de la operacin ser
substraccin (debido a que est dentro de los parntesis), seguido por la multiplicacin
y la adicin.

Cuando se analizan expresiones ms complejas, se torna ms difcil evaluar las


expresiones de forma infija. Por esto, la mayora de los compiladores normalmente
convierten las expresiones a forma postfija para que la evaluacin sea ms sencilla.

Ya que entender la evaluacin de expresiones en forma infija es difcil, se da una


solucin para encontrar si una expresin en forma infija es vlida o no.

Para evaluar una expresin, el primer paso es encontrar si la expresin aritmtica de


entrada es vlida o no, esto tiene un grado de dificultad. Se usa este ejemplo para
establecer cmo los compiladores usan las pilas para evaluar expresiones

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 91

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

eficientemente. Sin embargo, una solucin al problema para encontrar si la expresin es


vlida o no es convertir la expresin en su forma postfija.

Para llegar a la solucin de encontrar si una expresin aritmtica en forma infija es


vlida, se dejarn de lado ciertas restricciones de las expresiones aritmticas. Esto har
la solucin menos difcil.

Ejemplo 4.2

Considere las expresiones aritmticas escritas en C. Por conveniencia, se va a restringir


a una pequea versin. Se van a considerar expresiones aritmticas con operandos que
tengan constantes de enteros de dos dgitos, y/o caracteres simples del alfabeto A-Z o
a-z como identificadores (del tipo entero solamente). Adems, el conjunto de
operadores binarios permitidos para la construccin de expresiones aritmticas est
restringido al conjunto (+, -, *, /, %) como operadores binarios. Los operadores unarios +
y no sern usados. Las expresiones pueden tener parntesis en cualquier nivel.
Algunas de las expresiones vlidas son:
a + B / (12 * c)
(a+(b*c) ((2 + d) * (e % f)))/120
Algunas de las expresiones invlidas son:
(a + B)(c-d) error de sintaxis falta de Operador
(((b-2)*(b-2) faltan parntesis
Se escribe un programa completo en C que toma como entrada una expresin
aritmtica que sigue las reglas anteriores y muestra lo siguiente:
Si una expresin de entrada es sintcticamente correcta o no. Ejemplos de una
expresin correcta e incorrecta se dan a continuacin.
a + B / (12 * c)
Esta es una expresin correcta.
(((b-2)*(b_2)
Esta es una expresin incorrecta.
Los identificadores usados.
Las constantes usadas.
Los operandos usados.
El cdigo en C empieza aqu
1. #define SIZE 10
2. #include stdio.h
3. #include stdlib.h
4. #include string.h
5. typedef enum {falso, verdadero} boolean;

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 92

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

6. /* Prototipos para las funciones */


7. void removeDuplicatesChar(char*);
8. void removeDuplicatesInt(int*, int);
9. boolean isOperator(char);
10. boolean isOperand(char);
11. boolean isValidOperator(char);
12. void displayIdentifiers(char*);
13. void displayConstants(char*);
14. void displayOperators(char*);
15. /* Fin de prototipos */
16. /* El programa principal */
17. int main() {
18. Stack_type stack;
19. char prevSymbol, token, identifiers[SIZE],
operators[SIZE];
20. char originalExpr[40] = {' '}, expr[40] = {' '};
21. int length, i, j, nIden, nOp, nCon;
22. int constants[SIZE];
23. printf("Introduzca una expresin ... operadores
vlidos: +,-,*,/,%\n");
24. i = 0;
25. do {
26. scanf("%c", &originalExpr[i++]);
27. } while (originalExpr[i-1] != '\n');
28. /* Reemplazar la nueva lnea con el carcter null */
29. originalExpr[i-1] = '\0';
30. /* Remover espacios y copiar en otra variable */
31. length = strlen(originalExpr);
32. if (length == 0) {
33. printf("No hay expresin de entrada!\n");
34. return 0;
35. }
36. for (i = 0, j = 0; i < length; i++)
37. if (originalExpr[i] != ' ')
38. expr[j++] = originalExpr[i];
39. expr[j] = '\0';
40. printf("\nLa expresin de entrada es %s\n\n", expr);

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 93

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

41. /* Expresin de entrada conteniendo slo un carcter


*/
42. if (length == 1 && expr[0] == '(') {
43. printf("Expresin invlida!\n");
44. return 0;
45. }
46. /* Expresin de entrada conteniendo slo dos
caracteres */
47. if (length == 2) {
48. printf("Expresin invlida!\n");
49. return 0;
50. }
51. /* Revisar para ver si el primer y ltimo token */
52. /* en la exp. son correctas */
53. if (isOperator(expr[0]) || expr[0] == ')' || \
54. isOperator(expr[length - 1]) || \
55. expr[length - 1]== '(') {
56. printf("Expresin invlida!\n");
57. return 0;
58. }
59. /* Llegar a este punto en el algoritmo significa que
60. los dos finales de la cadena estn OK */
61. /* Algunas inicializaciones */
62. nIden = 0;
63. nOp = 0;
64. nCon = 0;
65. newStack(&stack);
66. if (expr[0] == '(')
67. push(&stack, expr[0]);
68. if (isalpha(expr[0])) {
69. identifiers[nIden] = expr[0];
70. nIden++;
71. }
72. /* Smbolo previo estar en prevSymbol para */
73. /* revisar el token que sigue es vlido o no */
74. prevSymbol = expr[0];
75. /* Recorre la expresin entera empezando de

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 94

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

76. el segundo token hasta el penltimo token */


77. i = 1;
78. /* Bucle se mueve desde 1 a longitud 2 */
79. while (i <= length - 1) {
80. token = expr[i];
81. if (token == '\0') /* Revisar por caracter nulo
*/
82. break;
83. /* Revisar tokens vlidos que siguen al operando
*/
84. if (isOperand(prevSymbol)) {
85. /* Si es una letra del alfabeto */
86. if (isalpha(prevSymbol)) {
87. if ((token != ')' &&
!isOperator(token))\
88. || isOperand(token)) {
89. printf("Expresin invlida!\n");
90. return 0;
91. }
92. }
93. else /* prevSymbol es un dgito
*/
94. if (isdigit(token)); /* Aceptable */
95. else
96. if ((token != ')' &&
!isOperator(token))\
97. || isOperand(token)) {
98. printf("Expresin invlida
!\n");
99. return 0;
100. }
101. }
102. /* Revisar tokens vlidos que siguen un operador
*/
103. if (isOperator(prevSymbol)) {
104. if ((token != '(' && !isOperand(token)) \
105. || isOperator(token)) {
106. printf("Expresin invlida!\n");
107. return 0;

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 95

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

108. }
109. }
110. /* Revisar tokens vlidos que siguen
111. un parntesis abierto */
112. if (prevSymbol == '(') {
113. if (token != '(' && !isOperand(token)) {
114. printf("Expresin invlida!\n");
115. return 0;
116. }
117. }
118. /* Revisar tokens vlidos que siguen
119. un parntesis cerrado */
120. if (prevSymbol == ')') {
121. if (token != ')' && !isOperator(token)) {
122. printf("Expresin invlida!\n");
123. return 0;
124. }
125. }
126. /* Revisar que los parntesis concuerden */
127. /* Colocar en la pila el token como un parntesis
128. abierto */
129. if (token == '(')
130. push(&stack,token);
131. /* Sacar el parntesis abierto de la pila si el
132. token es un parntesis cerrado */
133. if (token == ')') {
134. if (!isEmpty(&stack))
135. /* Sacar parntesis abierto */
136. pop(&stack);
137. else {
138. /* Cuando cierra parntesis ms que
abiertos */
139. printf("Expresin invlida!\n");
140. return 0;
141. }
142. }

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 96

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

143. /* Almacenar constantes, identificadores y operandos


*/
144. if (isalpha(token)) {
145. identifiers[nIden] = token;
146. nIden++;
147. }
148. if (isOperator(token)) {
149. operators[nOp] = token;
150. nOp++;
151. }
152. if (isdigit(prevSymbol))
153. if (prevSymbol == expr[0]) {
154. if (isdigit(token)) {
155. /* Convertir un carcter en dgito */
156. constants[nCon] = ((prevSymbol -
\
157. '0') * 10) + (token - '0');
158. nCon++;
159. }
160. }
161. else {
162. if (isdigit(token)) {
163. /* Convertir un carcter a dgito */
164. constants[nCon-1] = (constants\
165. [nCon - 1] * 10) + (token - '0');
166. //nCon++;
167. }
168. }
169. /* prevSymbol es otra cosa diferente a dgito */
170. else {
171. if (isdigit(token)) {
172. /* Convertir un carcter a dgito */
173. constants[nCon] = token - '0';
174. nCon++;
175. }
176. }
177. prevSymbol = token;

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 97

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

178. i++;
179. }
180. /* Alcanzar este punto en el algoritmo significa que
181. la expresin es vlida excepto por revisin de
parntesis
182. Se hace eso a continuacin. Si la pila no esta vaca,
183. Significa que hay parntesis extras abiertos o cerrados
*/
184. if (!isEmpty(&stack)) {
185. printf("Expresin invlida!\n");
186. return 0;
187. }
188. printf("La expresin de entrada es VALIDA!\n\n");
189. /* Muestra los identificadores usados en la expresin
*/
190. /* Remueve los duplicados antes de imprimirlos */
191. removeDuplicatesChar(identifiers);
192. printf("Identificadores: ");
193. if (nIden == 0)
194. printf("Ninguno\n\n");
195. else {
196. for (j =0; j < nIden; j++)
197. // No imprime si es colocado en 0
198. if (identifiers[j] != 0)
printf("%c ", identifiers[j]);
199. printf("\n\n");
200. }
201. /* Muestra las constantes usadas en la expresin */
202. /* Remueve duplicados antes de imprimir */
203. removeDuplicatesInt(constants, nCon);
204. printf("Constantes: ");
205. if (nCon == 0)
206. printf("Ninguno\n\n");
207. else {
208. for (j = 0; j < nCon; j++)
209. if (constants[j] != 0)
210. printf("%d ", constants[j]);
211. printf("\n\n");

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 98

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

212. }
213. /* Muestra operandos usados en la expresin */
214. /* Remueve duplicados antes de imprimir */
215. removeDuplicatesChar(operators);
216. printf("Operadores: ");
217. if (nOp == 0)
218. printf("Ninguno\n\n");
219. else {
220. for (j = 0; j < nOp; j++)
221. printf("%c ", operators[j]);
222. printf("\n\n");
223. }
224. return 0;
225. } /* Fin del programa principal */
El cdigo C termina aqu

El cdigo principal es auto-explicativo. Las otras funciones que se escribieron para este
programa se dan a continuacin.

El cdigo en C empieza aqu

/* Otras funciones */
1. /* Funcin que remueve duplicados de un arreglo de
caracteres */
2. void removeDuplicatesChar(char *input) {
3. int i, j, length;
4. char value;
5. length = strlen(input);
6. for (i = 0; i < length; i++) {
7. value = input[i];
8. for (j = i + 1; j < length; j++)
9. if (input[j] == value)
10. input[j] = 0; /* Colocandolo en 0 */
11. }
12. } /* Fin de la funcin */
13.
14. /* Funcin que remueve duplicados de un arreglo de
enteros */
15. void removeDuplicatesInt(int *input, int noOfItems) {

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 99

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

16. int i, j, value;


17. for (i = 0; i < noOfItems; i++) {
18. value = input[i];
19. for (j = i + 1; j < noOfItems; j++)
20. if (input[j] == value)
21. input[j] =0; /* Colocandolo en 0 */
22. }
23. }/* Fin de la funcin */
24.
25. /* Funcin que encuentra si el carcter de entrada es
un operador */
26. boolean isOperator(char token) {
27. char operators[5] = {'+', '-', '*', '/', '%'};
28. int i;
29. /* Revisa si el operador de entrada es vlido */
30. /* Retorna verdadero si es vlido, de lo contrario
falso */
31. for (i = 0; i < 5; i++)
32. if (token == operators[i])
33. return verdadero;
34. return falso;
35. }/* Fin de la funcin */
36.
37. /* Funcin que encuentra si el carcter de entrada es
un operando */
38. boolean isOperand(char token) {
39. /* Revisar si el operando de entrada es vlido */
40. /* Retorna verdadero si es vlido, de lo contrario
falso */
41. if (isdigit(token) || isalpha(token))
42. return verdadero;
43. return falso;
44. }/* Fin de la funcin */
45.
46. /* Funcin que encuentra si el operador es un operador
vlido */
47. boolean isValidOperator(char op) {
48. char operators[5] = {'+', '-', '*', '/', '%'};

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 100

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

49. int i;
50. /* Revisa si el operador de entrada es vlido */
51. /* Retorna verdadero si es vlido, de lo contrario
falso */
52. for (i = 0; i < 5; i++)
53. if (op == operators[i])
54. return verdadero;
55. return falso;
56. }/* Fin de la funcin */
El cdigo en C termina aqu

Use las funciones anteriores junto con las funciones de pila que se escribieron
anteriormente. La entrada y salida del programa se dan a continuacin:

Entrada:
Introduzca una expresin ... operadores vlidos: +,-,*,/,%
a + (b - c) + d 40
Salida:
Introduzca una expresin ... operadores vlidos: +,-,*,/,%
a + (b - c) + d - 40

La expresin de entrada es a+(b-c)+d-40

La expresin de entrada es VALIDA!

Identificadores: a b c d

Constantes: 40

Operadores: + -
Fin del Ejemplo 4.2

Se observa en el ejemplo anterior que escribir una solucin para evaluar una versin
simple de una expresin aritmtica es un poco compleja. Idealmente, las formas infijas
se convierten a notacin postfija. Aunque la conversin de infija a postfija parezca
compleja, usando una pila para realizar la conversin lo hace ms fcil. Una vez que se
tiene la expresin en forma postfija, se evala (en lugar de la forma infija) para obtener
el resultado. A continuacin se presentan los pasos para convertir formas infija a
postfija. Escribir el cdigo C para esto se puede realizar como un ejercicio.

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 101

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5.9 Conversin de Infijo a Postfijo

Usando una pila, se puede convertir una expresin de forma infija a postfija. Para
entender como esto se hace se asume lo siguiente:
Los operadores son +, *, /,-, y ().
+ tiene igual precedencia que .
*, / tienen mayor precedencia sobre + y .
() tiene la ms alta precedencia.

Considere la siguiente expresin:


x1 + (x2 x3) * x4 x5
El postfijo equivalente es como sigue:
x1 x2 x3 x4 * + x5 -
Ahora se convierte la forma infija a forma postfija usando una pila. La solucin empieza
con una pila vaca. Para cada token que se encuentra en la cadena de entrada (la
expresin infija), se toma una accin, ya sea para colocarlo en la pila o para colocarlo
en la cadena de salida. Los pasos para lograr esto se dan a continuacin:
Cuando se encuentra un operando, se aade a la cadena de entrada.
Cuando se encuentra un parntesis izquierdo, se coloca en la pila.
Cuando se encuentra un parntesis derecho, todos los elementos de la pila son
sacados a la cadena de salida hasta que un parntesis izquierdo sea sacado.
Ninguno de los parntesis se aaden a la cadena de salida.
Cuando se encuentra un operador, las siguientes reglas se aplican:
- El primer operador en la cadena de entrada se coloca (push) en la pila.
- Si el siguiente operador encontrado tiene una alta prioridad sobre el operador
en la pila, el operador se coloca (push) en la pila.
- Si el siguiente operador encontrado tiene menor o igual prioridad a los
operadores en el tope de la pila, todos los operadores de igual o mayor
prioridad son sacados y aadidos a la cadena de salida.
- Si el parntesis izquierdo ha sido colocado en la pila, todos los operadores
encontrados, hasta que un parntesis derecho sea encontrado, son colocados
en la pila.
Cuando se llega al final de la cadena, cualquier cosa que quedo en la pila se
retira y aade a la cadena de salida.
La cadena de salida, cuando la pila est vaca, est en forma postfija.
Ver la Tabla 4.1, la cual muestra cada paso para convertir la forma infija a postfija.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 102

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Token de
Aadido a la
la Cadena En la Pila Comentario
Cadena de Salida
de Entrada
Operando aadido a la cadena de
x1 x1
salida.

+ + Primer operador, colocado en la pila.

( Parntesis izquierdo, colocado en la


(
+ pila.
Operando aadido a la cadena de
x2 x1 x2
salida.
-
Parntesis izquierdo dentro de la pila,
- (
aade operador a la pila.
+
Operando aadido a la cadena de
x3 x1 x2 x3
salida.
Parntesis derecho encontrado.
Todos los operadores retirados junto
) x1 x2 x3 - + con los parntesis izquierdos y
aadidos a la cadena de salida. El
parntesis izquierdo es descartado.
* Operador con alta precedencia,
*
+ colocado en la pila.
Operando aadido a la cadena de
x4 x1 x2 x3 x4
salida.
Operador con baja precedencia.
Todos los otros operadores en la pila
- x1 x2 x3 x4 * + -
son sacados y aadidos a la cadena
de salida.
Operando aadido a la cadena de
x5 x1 x2 x3 x4 * + x5
salida.
Final de la cadena de entrada. Todos
Fin de los elementos de la pila han sido
x1 x2 x3 x4 * + x5 -
cadena retirados de la pila y aadidos a la
cadena de salida.

Tabla 4.1: Secuencia de Pasos a Convertir Forma Infija a Postfija

6. Evaluar una Expresin Postfija


Habiendo convertido una expresin de infijo a postfijo, se va a mostrar cmo evaluar la
expresin postfija. Los pasos son simples y se listan a continuacin:
Si se encuentra un operando, ste se coloca (push) en la pila.

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 103

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Si se encuentra un operador binario, sacar (pop) dos elementos del tope de la


pila. Evaluar la expresin binaria y colocar (push) el resultado en la pila.
Si se encuentra un operador unario, sacar un elemento del tope de la pila.
Evaluar la expresin unaria y colocar (push) el resultado en la pila.
Cuando se alcanza el final de la entrada, sacar el contenido de la pila, el cual es
el resultado de la expresin postfija.
Tabla 4.2 es una representacin de los pasos anteriores para la siguiente expresin
postfija:
15 2 + 10 3 2 * - *
La forma infija anterior es la que sigue:
(15 + 2) * (10 - 3 * 2)
El valor de la expresin anterior es 68.
Token de la
Cadena de En la Pila Comentarios
Entrada

15 15 Operando colocado en la pila.

2
2 Operando colocado en la pila..
15
+ es un operador binario. Sacar (pop) los 2
+ 17 elementos del tope, realizar la operacin
15+2 y almacenar el resultado en la pila.
10
10 Operando colocado en la pila.
17
3
3 10 Operando colocado en la pila.
17
2
3
2 Operando colocado en la pila.
10
17
6 * es un operador binario. Sacar los 2
* 10 elementos del tope, realizar la operacin
17 3*2 y almacenar el resultado en la pila.
- es un operador binario. Sacar los 2
4
- elementos del tope, realizar la operacin 10
17
- 6 y almacenar el resultado en la pila.
* es un operador binaria. Sacar los 2
* 68 elementos del tope, realizar la operacin 17
* 4 y almacenar el resultado en la pila.
Sacar el contenido de la pila, ese es el
Fin de cadena
resultado de la expresin postfija.

Tabla 4.2: Secuencia de Pasos para Evaluar la Expresin Postfija

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 104

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Se ha tomado el ejemplo de evaluacin de la expresin para ilustrar el uso de pilas. Las


pilas se pueden usar para evaluar cualquier tipo de expresin, mientras las reglas sean
claras acerca del uso de los operadores.

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 105

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que ha completado esta unidad, Ud. debe ser capaz de:
Definir la estructura de datos pila.
Explicar las diferentes operaciones definidas en la pila.
Describe las operaciones del TDA Pila.
Explica la implementacin de una pila usando un arreglo y una lista enlazada.
Discutir el uso de las pilas en la resolucin de problemas.

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 106

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 4: Examen de Autoevaluacin


1) Una pila es una estructura lineal en la cual los elementos pueden ser aadidos o
removidos de un slo extremo.
a) Verdadero
b) Falso

2) La pila tambin se conoce como ____________.


a) Lista FILO
b) Lista FIFO
c) Lista LIFO
d) Ninguna de las anteriores

3) Una lista de empuje hacia abajo (pushdown list) es otro nombre para cul de los
siguientes:
a) Una lista enlazada
b) Una cola
c) Una lista simple
d) Una pila

4) Cul de las siguientes son desventajas de implementar una pila como un arreglo?
a) El tamao de la pila es finito
b) El tamao de la pila es fijo
c) El tamao de la pila puede ser configurado dinmicamente
d) Ambas a y b

5) Una pila puede contener slo tipos de datos atmicos como integer, float, etc.
a) Verdadero
b) Falso

6) La operacin push en una pila no se puede usar para colocar(push) estructuras


completas.
a) Verdadero
b) Falso

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 107

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

7) La aplicacin que requiere remover los elementos insertados de primero es:


a) Una cola
b) Una lista enlazada
c) Una pila
d) Una lista simple

8) Sera apropiado usar una pila para almacenar elementos perecederos tales como
vegetales y carne de un supermercado?
a) Verdadero
b) Falso

9) Cuando se implementa una pila como lista enlazada, cul de los siguientes
representan una ventaja?
a) Provisin de una estructura esttica de datos
b) Provisin de una estructura dinmica de datos
c) El tamao de la pila no necesita ser determinado cuando se escribe un
programa
d) Ninguna de las anteriores

10) Las pilas son tiles en la evaluacin de expresiones aritmticas, si la entrada est
en la forma infija.
a) Verdadero
b) Falso

Unidad 4: Pila Libro 1: Estructura de Datos y Algoritmos 108

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Respuestas de la Unidad 4: Examen de Autoevaluacin


1) a
2) c
3) d
4) d
5) b
6) b
7) a
8) b
9) b y c
10) a

Libro 1: Estructura de Datos y Algoritmos Unidad 4: Pila 109

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 5: Laboratorio de Pila


Objetivos de Aprendizaje
Al final de esta unidad, Usted ser capaz de:
Aplicar el concepto de pila para resolver problemas simples.
Crear una pila y realizar sus operaciones en C.
Usar las operaciones de pilas en todo tipo de aplicaciones.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Laboratorio de Pila 111

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Ejercicios de Laboratorio
Una de las tareas que un compilador realiza para cualquier lenguaje de programacin
es determinar si las llaves que se abren { concuerdan en nmero con las llaves que se
cierran }. Esto es una revisin que cualquier compilador realiza. Escribir un programa
en C que tome una entrada de datos y revise que las llaves concuerden y muestre lo
siguiente:
Cuando las llaves que abren son ms que las llaves que cierran en el programa:
Error: No hay concordancia de parntesis que cierran
Cuando las llaves que cierran son ms que las llaves que abren en el programa:
Error: No hay concordancia de parntesis que abren
Cuando los parntesis que abren y cierran concuerdan:
Los parntesis que abren y cierran concuerdan
Tambin mostrar el nmero total de lneas ledas y el nmero de llaves que abren y
cierran encontrados en el programa, de la siguiente manera:
El nmero total de lneas ledas es 125
El nmero total de llaves que abren es 13
El nmero total de llaves que cierran es 12
Consejos tiles:
Usar la pila para proveer la estructura de datos correcta para solucionar el
problema.
Usar la pila para colocar las llaves que abren.
Cuando se encuentran llaves que cierran, sacar las llaves que abren de la pila.
Salir del programa cuando se encuentre la primera incongruencia.
Recordar los siguientes puntos:
- Una concordancia ocurre cuando las ltimas llaves que cierran se encuentran y
una operacin pop se realiza en la pila. La pila est vaca.
- Cuando un parntesis es encontrado y no hay nada para sacar de la pila,
significa que hay menor nmero de llaves que abren comparado con las llaves
que cierran.
- Al final del archivo, si la pila no est vaca, significa que hay menor nmero de
llaves que cierran comparados con las llaves que abren.

Unidad 5: Laboratorio de Pila Libro 1: Estructura de Datos y Algoritmos 112

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 6: Colas
Objetivos de Aprendizaje
Al final de esta unidad, usted ser capaz de:
Definir la estructura de datos de cola.
Explicar las operaciones del TDA en cola.
Discutir la implementacin de una cola como arreglo.
Explicar las implementaciones de una cola como arreglo circular.
Describir la implementacin de una cola como lista enlazada.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 113

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. Preliminares de Cola
En el lenguaje comn, una cola es una lnea de espera. Normalmente, la primera
persona o elemento de la cola ser el primero en ser atendido. Se puede definir una
cola, en lenguaje de computacin, como una lista en la que sus elementos se insertan
en un extremo de la lista y se retiran del otro extremo. Una cola tambin se denomina
una lista primero en entrar, primero en salir o simplemente FIFO (First-In First-Out).

Debido a que una cola maneja la llegada y el retiro de elementos, ambos extremos son
importantes. Observe la Figura 6.1 que ilustra la representacin de una cola.

Figura 6.1: Cola de Personas

Las colas se pueden definir como un TDA, del siguiente modo:


new (queue): Crea una nueva cola que est vaca.
enqueue(queue, element): Inserta el elemento element al final de la cola.
dequeue(queue): Elimina el elemento de la cabeza o frente de la cola.
front(queue): Devuelve el elemento de la cabeza o frente de la cola.
isempty(queue): Devuelve verdadero si la cola est vaca, falso en caso
contrario.
Como las estructuras de datos listas y pilas, new y enqueue son las operaciones
bsicas de una cola. Las dems operaciones se pueden describir en trminos de new y
enqueue.

1.1 Definir dequeue utilizando new y enqueue

La operacin dequeue retira un elemento de la cabeza o frente de una cola. Ahora se


proceder a definir la operacin dequeue que utiliza new y enqueue. La operacin
dequeue(new(queue)) arrojar un error cuando la cola no tenga elementos para
sustraer. Por lo tanto, la operacin dequeue sobre new(queue) se puede escribir
como sigue:

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 114

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

dequeue(new(queue)) = error
Ahora se va a comprender la operacin dequeue en trminos de enqueue(queue,
element). Se puede notar que queue puede ser cualquier cola.
Si queue est vaca, la operacin enqueue(queue, element) generar una cola
con slo un elemento denominado element. Cuando se ejecuta la operacin dequeue
sobre queue, el elemento element se retira y se devuelve la cola vaca.
Esta parte de la operacin se puede escribir como:
dequeue(enqueue(queue, element)) =
if isempty(queue) then new (queue)
Sin embargo, si queue no est vaca, entonces enqueue(queue, element)
permitir que queue resulte con element agregado al final de la cola. El resultado es el
mismo que dequeue(enqueue(queue, element)). Esto implica que enqueue y
dequeue estn operando sobre puntos independientes de la cola.
Nota: Sin este axioma, no se tendr forma de figurar que enqueue y dequeue estn
operando en puntos independientes de la cola, es decir, en la cabeza y el final de la
cola.
Por lo tanto, la operacin dequeue se puede escribir completamente como:
dequeue(enqueue(queue, element)) =
if isempty(queue) then new(queue)
else
enqueue(dequeue(queue, element))
Se intentar comprender esto con un ejemplo. Se utilizar una cola de ejemplo
denominada myQueue para explicar las operaciones sobre la cola utilizando las
operaciones bsicas.

Ejemplo para ilustrar dequeue utilizando new

Se va a crear una nueva cola llamada myQueue. Cuando se crea una cola utilizando la
operacin new, slo se crea una cola vaca. Aqu la operacin new sobre myQueue
devuelve un myQueue vaco. Cuando se pasa esta myQueue vaca a la operacin
dequeue devolver un error al no poder eliminar un elemento de una cola vaca.

Ejemplo para ilustrar dequeue usando enqueue en una Cola vaca

Se va a ver la operacin dequeue usando enqueue en myQueue. Asuma que myQueue


es una cola vaca. Se va a agregar el elemento Christopher a myQueue como sigue:
enqueue(myQueue, Christopher)
Hay un elemento en myQueue como resultado de la operacin anterior. La cola
myQueue ahora se pasa a la operacin dequeue. Ya que hay slo un elemento en la

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 115

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

cola, la operacin dequeue lo retira y revierte la cola a su forma original, es decir, una
cola vaca.
dequeue(enqueue(myQueue, element)) =
if isempty(myQueue) then new(myQueue)
La operacin anterior slo es un mtodo de declaracin que cuando se pasa una
myQueue vaca a enqueue y despus a dequeue, es equivalente a new(myQueue), ya
que el lado izquierdo y derecho del operador = termina en un myQueue vaco.

Ejemplo para ilustrar dequeue usando enqueue en una Cola no vaca

Suponga que myQueue no est vaca y actualmente presenta los siguientes nombres:

Lydia Sam Bill Martin

Lydia est en la cabeza de la cola y Martin est al final de la cola. Si 'Christopher'


se une a la cola, los elementos de la cola estarn posicionados como:
Lydia Sam Bill Martin Christopher
As, enqueue(myQueue, Christopher) producir una cola con los cinco
elementos anteriores. Ahora, si se pasa myQueue en este nuevo estado a la operacin
dequeue, se sacar de la cabeza de la cola a Lydia y la cola resultante ser como:
Sam Bill Martin Christopher
A diferencia de una pila, la adicin y eliminacin de una cola ocurre en terminales
diferentes. La parte else del axioma intenta mostrar lo siguiente:
else enqueue(dequeue(queue, element))
Si myQueue no est vaca, simplemente se declara que:
dequeue(enqueue(myQueue, Christopher))=
enqueue(dequeue(myQueue), Christopher)
Se ha visto que dequeue(enqueue(myQueue, element)) genera una cola que
consiste de cuatro elementos con Sam en la cabeza de myQueue y Christopher al
final de myQueue.

Ahora se va a ver lo que genera enqueue(dequeue(myQueue, Christopher)).

Asuma que myQueue est conformada por:


Lydia Sam Bill Martin
Ahora se lleva a cabo dequeue en myQueue. La operacin genera:
Sam Bill Martin

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 116

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

En este nuevo estado myQueue se pasa a enqueue, despus de la insercin de


Christopher, se tienen cuatro elementos en la cola.
Sam Bill Martin Christopher
Se obtiene la misma myQueue que al aplicar dequeue(enqueue(myQueue,
element). Este axioma es el ms importante para una cola porque revela que la
insercin y eliminacin de elementos en una cola no son dependientes entre s.

1.2 Definir front con new y enqueue

La operacin front devuelve el elemento situado en la cabeza o al frente de la cola.

Considere por ejemplo la siguiente operacin:


front(new(queue)) = error
La operacin new devuelve una cola vaca y front devuelve un error, porque no puede
devolver el elemento al frente de una cola vaca.

Cuando la operacin front(enqueue(queue, element)) se ejecuta sobre una cola


vaca, devuelve element, que implica que es el nico elemento de la cola y que es
manejado como la cabeza de la cola. Pero cuando queue no est vaca, el resultado es
el mismo que el resultado de la operacin front(queue)(es decir, se devolver el
elemento de la cabeza de la cola).Esto implica que la operacin enqueue agrega un
elemento al final de la cola, y no en la cabeza de la cola.

La operacin anterior se puede declarar como:


front(enqueue(queue, element)) =
if isempty(queue) then element
else
front(queue)
Ejemplo para ilustrar front usando new

Tomando el mismo ejemplo de myQueue, se sabe que la pila est vaca, as la


operacin front devuelve un error si todava no hay elementos en myQueue.

Ejemplo para ilustrar front usando enqueue en una cola vaca

Se va a tomar el ejemplo de myQueue nuevamente. Si myQueue est vaca, al agregar el


elemento Christopher tendr slo un elemento. La cabeza de la cola es ese nico
elemento en la cola. As:
front(enqueue(myQueue, Christopher)) = Christopher

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 117

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejemplo para ilustrar front Usando enqueue en una Cola no-vaca

Se va a asumir que myQueue no est vaca y tiene los siguientes cuatro elementos:
Lydia Sam Bill Martin
Lydia est al frente de la cola. Si myQueue se pasa como argumento a enqueue, y se
agrega Christopher, la cabeza de la cola myQueue todava es Lydia. Al agregar
Christopher a myQueue, en la cabeza todava est Lydia porque la adicin se
ha llevado a cabo al final de la cola.
front(enqueue(myQueue, Christopher)) = Lydia

1.3 Definir isempty con new y enqueue

Se crea una nueva cola vaca. Para declararla se escribe la operacin:


isempty(new) = true
Esta es una operacin verdadera.

Ahora se va a definir isempty usando enqueue.


isempty(enqueue(queue, element)) = false
Ejemplo para ilustrar isempty usando new

Tomando el mismo ejemplo de myQueue, se puede ver que una nueva pila est vaca,
as resulta el valor true con la operacin isempty.

Ejemplo para ilustrar isempty usando enqueue en una Cola vaca

Si la operacin enqueue se realiza sobre una myQueue vaca y se agrega


Christopher, myQueue llega a ser no vaca y as isempty devolver falso.

Ejemplo para ilustrar isempty usando enqueue en una Cola no vaca

Asuma que myQueue no est vaca, se realiza la operacin enqueue y se agrega


Christopher. Anteriormente no estaba vaca y continuar as incluso cuando se
agregue Christopher . As la operacin isempty devolver falso.
Basndose en las reglas de operaciones sobre una cola se pueden resumir los axiomas
como sigue:
Para todo queue y element es vlido:
dequeue(new(queue)) = error
dequeue(enqueue(queue, element)) =
if isempty(queue) then new(queue)
else
enqueue(dequeue(queue, element))

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 118

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

front(new(queue)) = error
front(enqueue(queue, element)) =
if isempty(queue) then element
else
front(queue)
isempty(new(queue)) = true
isempty(enqueue(queue, element)) = false
A continuacin se va a seguir con la implementacin de colas teniendo en cuenta la
comprensin de las operaciones que se han aprendido. Primero se implementar una
cola como arreglo.

2. Implementar las Colas como Arreglos


Siempre se debe vigilar ambos extremos de la cola. Se puede mantener la cabeza de la
cola siempre en la posicin 0 del arreglo. Agregar un elemento a la cola, simplemente
significa incrementar el contador que muestra el final de la cola. Sin embargo, eliminar
un elemento de la cola resulta complejo, porque se debe eliminar el primer elemento del
arreglo y se deben mover los dems elementos. Este proceso resultar muy lento
cuando el tamao de la cola sea grande.

A continuacin se implementan cada una de las operaciones de cola como funciones C.

El cdigo C empieza aqu...


1. typedef enum {falso, verdadero} boolean;
2. #define QUEUEMAX 100
3. #include stdio.h
4. typedef int Element_type;
5. typedef struct queuer {
6. int front;
7. int rear;
8. Element_type queue[QUEUEMAX];
9. } Queue_type;
El cdigo C termina aqu

Se tienen dos variables definidas como parte de la estructura de la cola, una para
indicar el frente o cabeza de la cola y otra (rear) para indicar el final de la cola.

El cdigo C empieza aqu...


1. /* Prototipos de funciones */
2. void newQueue(Queue_type *queue);
3. void enqueue(Queue_type *q_ptr, Element_type elem);

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 119

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

4. Element_type dequeue(Queue_type *q_ptr);


5. Element_type front(Queue_type *q_ptr);
6. int isempty(Queue_type *q_ptr);
7. int isFull(Queue_type *q_ptr);
El cdigo C termina aqu

A continuacin se dan las implementaciones para las operaciones sobre una cola.

2.1 Crear una Nueva Cola

El cdigo C empieza aqu...


1. /* New inicializa la cola a un estado vaco */
2. void newQueue(Queue_type *q_ptr) {
3. q_ptr->front = 0;
4. q_ptr->rear = -1;
5. }
El cdigo C termina aqu

El frente (front) de la cola se inicializa en 0 y permanecer inalterado a lo largo


de la aplicacin. El final (rear) est inicialmente colocado a 1. Esto tambin indica
que una cola est vaca.

En seguida se dan las implementaciones para las operaciones de cola. Al nivel TDA se
utilizan enqueue y dequeue para insercin y eliminacin respectivamente.

2.2 Insertar en una Cola

Para insertar un elemento en una cola, se verifica primero si la cola est llena.

El cdigo C empieza aqu...


1. /* Insertar un elemento en Q */
2. void enqueue(Queue_type *q_ptr, Element_type elem){
3. if (isFull(q_ptr))
4. return;
5. else {
6. q_ptr->rear++;
7. q_ptr->queue[q_ptr->rear]= elem;
8. return;
9. }
10. }

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 120

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

El cdigo C termina aqu

Dado que esto es una implementacin como arreglo, no se cambia el valor de front. El
valor de rear se incrementa en 1 cada vez que se agrega un elemento a la cola.

2.3 Eliminar de una Cola

Se tendrn que desplazar elementos del arreglo cada vez que se retire un elemento de
la cola.

El cdigo C empieza aqu...

1. /* Eliminar un elemento de Q */
2. Element_type dequeue(Queue_type *q_ptr) {
3. Element_type element;
4. int i;
5. if (isempty(q_ptr))
6. return -1;
7. else {
8. element = q_ptr->queue[q_ptr->front];
9. q_ptr->rear--;
10. for (i = 0; i <= q_ptr->rear; i++)
11. q_ptr->queue[i] = q_ptr->queue[i + 1];
12. return element;
13. }
14. }
El cdigo C termina aqu

Esta funcin requiere un manejo cuidadoso. Note que cada vez que se elimina un
elemento de la cola, se desplazan los dems elementos. Por eso no se cambia el valor
de front durante las operaciones de cola. Sin embargo, el valor de rear se
decrementa.

2.4 Encontrar la Cabeza de la Cola

Esta es una funcin muy simple de implementar.

El cdigo C empieza aqu...


1. /* Operacin front */
2. Element_type front(Queue_type *q_ptr) {
3. if (isempty(q_ptr))

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 121

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

4. return -1;
5. else
6. return q_ptr->queue[q_ptr->front];
7. }
El cdigo C termina aqu

2.5 Determinar la Condicin Vacia y Llena de una Cola

Estas dos funciones son requeridas por otras funciones para verificar cundo la cola
est vaca o llena (Empty y Full).

El cdigo C empieza aqu...


1. /* Para verificar si Q est vaca */
2. int isempty(Queue_type *q_ptr) {
3. if(q_ptr->rear == -1)
4. return (1);
5. else
6. return (0);
7. }
8. /* Para verificar si Q est llena */
9. int isFull(Queue_type *q_ptr) {
10. if(q_ptr->rear == QUEUEMAX - 1)
11. return (1);
12. else
13. return (0);
14. }
El cdigo C termina aqu

Se ha discutido acerca de la creacin de colas nuevas y la insercin y eliminacin de


elementos en una cola. A continuacin se discute la funcin sizeOfQueue.

sizeOfQueue es una funcin muy simple que se utiliza para encontrar la longitud de la
cola. Una sugerencia para escribir la operacin es que esta funcin verifique la
condicin isempty

Seguidamente, se muestra la funcin main que usa las funciones de la cola.

El cdigo C empieza aqu...


1. main() {
2. Queue_type queue;

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 122

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

3. Element_type elem;
4.
5. newQueue(&queue);
6.
7. printf("Introduzca elementos (caracteres) a almacenar
en la cola:\n");
8. while ((elem = getchar()) != '\n') {
9. enqueue(&queue, elem); // Insertar en la cola
10. printf("\tEl elemento ingresado en la cola es
:%c\n",elem);
11. }
12. printf("\nEliminando elementos de la cola:\n");
13. while (!isempty(&queue)) {
14. elem = dequeue(&queue); // Elimina de la cola
15. printf("El elemento eliminado es %c\n", elem);
16. }
17. if (dequeue(&queue) == -1)
18. printf("\nLa cola esta vaca: No puede realizar \
19. la operacin eliminar!\n");
20. return 1;
21. }
El cdigo C termina aqu

Si se ejecuta el programa main con las funciones de cola y la entrada this is a


new queue se obtiene la siguiente salida:
El elemento ingresado en la cola es :t
El elemento ingresado en la cola es :h
El elemento ingresado en la cola es :i
El elemento ingresado en la cola es :s
El elemento ingresado en la cola es :
El elemento ingresado en la cola es :i
El elemento ingresado en la cola es :s
El elemento ingresado en la cola es :
El elemento ingresado en la cola es :a
El elemento ingresado en la cola es :
El elemento ingresado en la cola es :n
El elemento ingresado en la cola es :e
El elemento ingresado en la cola es :w

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 123

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

El elemento ingresado en la cola es :


El elemento ingresado en la cola es :q
El elemento ingresado en la cola es :u
El elemento ingresado en la cola es :e
El elemento ingresado en la cola es :u
El elemento ingresado en la cola es :e

Eliminando elementos de la cola:


El elemento eliminado es t
El elemento eliminado es h
El elemento eliminado es i
El elemento eliminado es s
El elemento eliminado es
El elemento eliminado es i
El elemento eliminado es s
El elemento eliminado es
El elemento eliminado es a
El elemento eliminado es
El elemento eliminado es n
El elemento eliminado es e
El elemento eliminado es w
El elemento eliminado es
El elemento eliminado es q
El elemento eliminado es u
El elemento eliminado es e
El elemento eliminado es u
El elemento eliminado es e

La cola esta vaca: No puede realizar la operacin


eliminar!
Se encuentra que el elemento en la cabeza de la cola, es decir t en este caso, es el
primer elemento que se ha ingresado. Tambin se observa que los elementos de la cola
han sido retirados en el orden que se han ingresado, a diferencia de una pila. La ltima
lnea de la salida muestra que no se puede retirar ningn elemento de una cola vaca.

A continuacin se presenta un segundo mtodo para la operacin de eliminacin.

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 124

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

2.6 Operacin de Eliminacin: Otra Solucin

En la operacin de eliminacin discutida anteriormente, se movieron los elementos en el


momento que un elemento era retirado de la cola. Si se quiere evitar tener que empujar
elementos por cada eliminacin, se debe cambiar el valor de front cada vez que se
lleva a cabo una eliminacin, manteniendo vacante las posiciones de la cabeza desde
donde fueron retirados los elementos.

As, se puede tener dos formas de manejar el mtodo de eliminacin. Se va a


comprender la diferencia entre los dos mtodos con la ayuda de un ejemplo.

Asuma la siguiente secuencia de eventos para una cola. Se mostrar grficamente el


estado de la cola despus de cada operacin. Se asume que el tamao del arreglo es
10.

Operaciones de Cola
Insertar: lotus
Insertar: rose
Insertar: orchids
Eliminar
Insertar: hyacinth
Insertar: lily
Insertar: daisies
Eliminar
Eliminar
Insertar: marigold
Insertar: bluebells
Primer mtodo

Con la eliminacin, el valor de front queda en la posicin 0 y los dems elementos


quedan desplazados.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 125

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 6.2: Insercin y Eliminacin de Elementos: Primer Mtodo

La Figura 6.2 muestra los diferentes estados de la cola para las 11 operaciones de cola
dadas anteriormente. Se puede notar que cada eliminacin (4, 8 y 9 en la Figura 6.2)
desplaza elementos de la cola. De este modo, hay un recorrido involucrado en cada
eliminacin. En cada eliminacin front queda en la posicin 0.

Segundo Mtodo

Con la eliminacin, cambia el valor de front y los dems elementos no son


desplazados.

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 126

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Figura 6.3: Insercin y Eliminacin de Elementos: Segundo Mtodo

En la Figura 6.3 se observa que las posiciones desde las que se retiran elementos,
quedan vacantes. Cada eliminacin cambia el valor de front. En esta figura, el valor
de front ha sido cambiado en 4, 8 y 9. Con dos inserciones ms, la cola estar llena
incluso aunque las posiciones del frente del arreglo estn vacantes.

Ambos mtodos de eliminacin tratados anteriormente tienen ciertas desventajas. Para


superarlas, se puede implementar una cola como un arreglo circular.

3. Usar Arreglos Circulares


Un arreglo circular es uno en el que el primer elemento del arreglo es adyacente al
ltimo elemento del arreglo. La Figura 6.4 muestra un arreglo lineal y su arreglo circular
equivalente. El nmero total de elementos que se tienen en la cola es 16, que es el valor
inicializado en ARRAYMAX. El arreglo lineal puede tener elementos desde la posicin 0 a
ARRAYMAX-1. En la Figura 6.4, el frente de la cola est en el ndice 4 del arreglo lineal y
el final de la cola est en el ndice 12. Hay posiciones vacas al visualizar el arreglo
lineal doblado, en donde el ndice 0 est a la izquierda del ndice 15. Esto da un arreglo
circular. En el arreglo circular, se ve que hay posiciones 0, 1, , CIRCULARMAX-1.
El frente y final de la cola continan en los ndices 4 y 12 respectivamente.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 127

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 6.4: Arreglo Circular


De la Figura 6.4, es claro que cuando se est moviendo en el arreglo circular, el primer
elemento 0, se obtiene de CIRCULARMAX-1. Se puede construir una sentencia if,
como:
if (cell >= CIRCULARMAX-1)
cell = 0;
else
cell++;
Esta es simplemente la propiedad del arreglo circular vista como un arreglo lineal. La
tcnica mostrada es uno de los mtodos estndar de recorrido a travs de una lista

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 128

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

circular. En un arreglo circular, front se incrementa cuando se realiza una eliminacin


y rear se incrementa cuando se inserta un elemento en la cola. Si hay slo un
elemento en la cola, front y rear apuntan a la misma celda. En este caso, si se
extrae un elemento, front estar un paso adelante de rear. Esto indicar el estado de
una cola vaca.

De manera similar, en una representacin de arreglo circular, se considera que una cola
est llena cuando front est un paso adelante de rear. Observe la Figura 6.5.

Figure 6.5: Colas Vacas y Llenas

La Figura 6.5 muestra una cola vaca y una cola llena, donde front y rear estn
exactamente en la misma situacin.
La Figura tambin muestra la desventaja inherente de arreglos circulares al describir
una cola vaca o llena.
Para distinguir entre una cola vaca y una cola llena, se pueden adoptar una de las
siguientes soluciones:
Se pueden tener variables booleanas que indiquen si la cola est llena o vaca.
Se puede dejar explcitamente una celda en blanco entre front y rear. As, la
cola estar llena cuando haya una celda vaca entre front y rear.
Se pueden usar nmeros negativos para representar front y/o rear e indicar
que una cola est vaca. Nuevamente, aqu es importante mantener el tamao
de la cola.
Nota: No se discutirn sobre cmo se implementan estas soluciones ya que esto va
ms all del alcance de este curso.

A continuacin se aprender acerca de cmo se pueden utilizar listas enlazadas para


implementar una cola.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 129

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

4. Colas como Listas Enlazadas


La discusin de colas como arreglos es complicada ya que se deben visualizar como
arreglos circulares. Manejar colas vacas y colas llenas no es simple. Pero implementar
colas como listas enlazadas, quizs resulte tan simple como implementar pilas usando
listas enlazadas. Se tendr que mantener dos punteros, front y rear, que apuntarn
al frente y al final de la cola respectivamente.

El cdigo C empieza aqu...


1. typedef enum {falso, verdadero} boolean;
2. /* Tipo de dato definido por el usuario, para la cola
*/
3. typedef int Element_type;
4.
5. typedef struct node {
6. Element_type info;
7. struct node *next;
8. } Node_type;
9.
10. typedef struct queuer {
11. Node_type *front;
12. Node_type *rear;
13. } Queue_type;
El cdigo C termina aqu

Aqu se muestran los diversos prototipos de funciones para las operaciones sobre colas.
/* Prototipos de Funciones */
Node_type *createNode(Element_type);
void newQueue(Queue_type *);
boolean isEmpty(Queue_type *);
Element_type front(Queue_type *);
void enqueue(Queue_type *, Element_type);
Element_type dequeue(Queue_type *);

4.1 Implementar createNode()

El cdigo C empieza aqu...


1. /* Crear un nuevo nodo */
2. Node_type *createNode(Element_type element) {
3. Node_type *node;

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 130

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

4. node = (Node_type *) malloc(sizeof(Node_type));


5. node->info = element;
6. node->next = NULL;
7. return node;
8. }
El cdigo C termina aqu

La funcin createNode simplemente crea un nodo.

4.2 Implementando newQueue()

La operacin newQueue crea una cola nueva colocando front y rear a NULL.

El cdigo C empieza aqu...


1. /* Crear una cola nueva */
2. void newQueue(Queue_type *queue) {
3. queue->front = NULL;
4. queue->rear = NULL;
5. }
El cdigo C termina aqu

4.3 Implementar isempty()

Esta operacin es bastante simple ya que queue->front indica directamente si est


vaco o no. Si queue->front es un valor NULL, entonces est vaco.

El cdigo C empieza aqu...


1. /* Para descubrir si la cola est vaca */
2. boolean isempty(Queue_type *queue) {
3. if (queue->front == NULL)
4. return verdadero;
5. else
6. return falso;
7. }
El cdigo C termina aqu

4.4 Implementar front()

Simplemente se prueba si la cola est vaca, en cuyo caso devuelve error. Si la cola no
est vaca, devuelve directamente el front de la cola como (queue->front)->info.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 131

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

El cdigo C empieza aqu...


1. /* Para obtener el elemento que est al frente de la
cola */
2. Element_type front(Queue_type *queue) {
3. if (!isempty(queue))
4. return ((queue->front)->info);
5. else
6. return (-1); /*Devuelve -1 cuando la cola est
vaca */
7. }
El cdigo C termina aqu

4.5 Implementar enqueue()

Agregar un elemento a la cola depende de si la cola est vaca o no. Si est vaca, se
puede agregar al frente de la cola, sino necesita agregarse al final de la cola.

El cdigo C empieza aqu...


1. /* Agregar un elemento a la cola */
2. void enqueue(Queue_type *queue, Element_type element) {
3. Node_type *node;
4.
5. node = createNode(element);
6. if (queue->front == NULL){ /*en una Q cuyo frente es
NULL*/
7. queue->front = node;
8. queue->rear = node;
9. }
10. else { /* agregar al final de Q */
11. queue->rear->next = node;
12. queue->rear = node;
13. }
14. }
El cdigo C termina aqu

4.6 Implementar dequeue()

Cuando la cola est vaca, no hay nada que retirar. En este caso, se devuelve un error.
Si hay slo un elemento en la cola, entonces la cola llega a estar vaca. En caso

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 132

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

contrario, se elimina el elemento al frente de la cola y los punteros se arreglan de


acuerdo a esto.

El cdigo C empieza aqu...


1. /* Eliminar un elemento de la cola */
2. Element_type dequeue(Queue_type *queue) {
3. Node_type *q;
4. Element_type elem;
5.
6. if (isempty(queue))
7. return -1; /* Cuando la cola est vaca */
8. if (queue->front == queue->rear) {
9. elem = (queue->front)->info;
10. free(queue->front);
11. queue->front = NULL;
12. queue->rear = NULL;
13. }
14. else {
15. q = queue->front;
16. elem = q->info;
17. queue->front = (queue->front)->next;
18. free(q);
19. }
20. return elem;
21. }
El cdigo C termina aqu

Un ejemplo de main() para invocar a todas las operaciones de Colas

Se tiene una funcin main que muestra el uso de las diversas operaciones de colas. La
funcin main se parece a la que se escribi para la implementacin de una cola como
arreglo, con algunos cambios menores para manejar enteros en lugar de obtener
caracteres como entrada.

El cdigo C empieza aqu...


1. int main() {
2. Queue_type queue;
3. Element_type elem;
4.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 133

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5. newQueue(&queue);
6.
7. printf("Introduzca los elementos (numeros) a almacenar
en la \
8. cola, finalice con -9999\n");
9. scanf("%d", &elem);
10. do {
11. if (elem == -9999)
12. break;
13. enqueue(&queue, elem); // Insertar en queue
14. printf("\t El elemento ingresado en la cola es
:%d\n",(&elem));
15. scanf("%d", &elem);
16. } while (elem != -9999);
17.
18. printf("\nEliminando elementos de la cola:\n");
19. while (!isempty(&queue)) {
20. elem = dequeue(&queue); // Retirar de queue
21. printf("El elemento eliminado es %d\n", elem);
22. }
23. if (dequeue(&queue) == -1)
24. printf("\nLa cola est vaca: No puede realizar \
25. la operacin eliminar!\n");
26. return 1;
27. }
El cdigo C termina aqu

A continuacin se muestra la entrada y salida del programa usando una cola como lista
enlazada:

Entrada:
Introduzca los elementos (numeros) a almacenar en la cola,
finalice con -9999
198
El elemento ingresado en la cola es :198
201
El elemento ingresado en la cola es :198
302

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 134

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

El elemento ingresado en la cola es :198


-67
El elemento ingresado en la cola es :198
-100
El elemento ingresado en la cola es :198
234
El elemento ingresado en la cola es :198
10007
El elemento ingresado en la cola es :198
-9999
Salida:
Eliminando elementos de la cola:
El elemento eliminado es 198
El elemento eliminado es 201
El elemento eliminado es 302
El elemento eliminado es -67
El elemento eliminado es -100
El elemento eliminado es 234
El elemento eliminado es 10007
La cola est vaca: No puede realizar la operacin
eliminar!
Se ha discutido la implementacin de una cola como arreglo y como lista enlazada. Los
puntos tratados sobre cundo usar arreglos y listas enlazadas en pilas se mantienen
tambin para la implementacin de colas.

De hecho, no se ha presentado una implementacin enlazada de una cola llena. En una


implementacin enlazada, una cola est llena slo cuando malloc devuelve NULL.
Malloc devuelve NULL slo cuando el sistema no es capaz de asignar ms memoria
para los nodos. Considere este ejercicio y escriba la funcin. Sin embargo, probar la
funcin es difcil, ya que no se est seguro cundo podr faltar memoria.

5. Aplicaciones de Colas
A continuacin se discuten algunas aplicaciones de colas.

5.1 Implementando Colas de Impresin

En los sistemas operativos, las impresoras y otros dispositivos que inherentemente no


pueden ser compartidos, son compartidos. Los usuarios simplemente envan sus
requerimientos de impresin a la impresora compartida. Estos trabajos de impresin son
ubicados en una cola de impresin y se imprimen secuencialmente.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 135

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5.2 Datos del Buffer

Hay diversas aplicaciones en las que los dispositivos y/o procesos se comunican unos a
otros. Debido a la diferencia en las velocidades de sus operaciones, hay la necesidad
de almacenar los datos que estn siendo transferidos entre ellos. Las colas son una
opcin obvia a usarse para tales aplicaciones. De hecho, todos los buffers son
conceptualmente colas.

5.3 Simulacin de Modelos de Lneas de Espera

Las colas son estructuras de datos naturales que se usan para la simulacin de
modelos de lneas de espera. Esto puede involucrar cualquier situacin de la vida real,
como trabajos que esperan ser procesados por las maquinarias de una planta industrial,
tareas que esperan ser ejecutadas en un computador, clientes que esperan ser
atendidos en un banco, entre otros.

5.4 Recorrido Breadth First de rboles

Existen numerosas aplicaciones, incluyendo juegos que requieren el uso de recorrido


Breadth First de rboles. Las colas son buenas estructuras de datos para implementar
este algoritmo.

5.5 Sistemas Operativos

En los sistemas operativos, muchos procesos compiten y hacen uso de los recursos
escasos de la computadora, como CPU, memoria principal y dispositivos I/O. Por lo
tanto, cuando un proceso est usando algn recurso en particular, los dems procesos
deben esperar. Los sistemas operativos hacen uso de algoritmos de planificacin para
asignar recursos a los procesos en espera. Las colas se pueden utilizar para la
implementacin de diversos mdulos de los sistemas operativos.

5.6 Administracin del Trfico de la Red

Cuando los datos se transmiten a travs de redes, una cola es una excelente estructura
de datos para almacenar los datos y permitir que los elementos de datos se ordenen.

5.7 Aplicaciones Comerciales en Lnea

Las colas se pueden usar como estructuras de datos vitales en muchas aplicaciones
comerciales en lnea, como el procesamiento de los requerimientos del cliente, rdenes
y tareas.

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 136

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Resumen
Ahora que ha completado esta unidad, Ud. debe ser capaz de:
Definir la estructura de datos cola.
Explicar las operaciones del TDA en colas.
Implementar una cola como arreglo.
Explicar las implementaciones de una cola como arreglo circular.
Describir la implementacin de una cola como lista enlazada.

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 137

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 6: Examen de Autoevaluacin


1) Una Cola tambin se denomina ________.
a) Lista FIFO
b) Lista LIFO

2) Cul de las siguientes operaciones es realizada por enqueue?


a) Agregar un elemento al frente de la cola
b) Eliminar un elemento del final de la cola
c) Eliminar un elemento del frente de la cola
d) Agregar un elemento al final de la cola

3) Cul de las siguientes operaciones es realizada por dequeue?


a) Eliminar un elemento del final de la cola
b) Encontrar el elemento que est al frente de la cola
c) Eliminar un elemento del frente de la cola
d) Ninguna de las anteriores

4) Es correcto el axioma:
dequeue(enqueue(queue,element)) = if isempty(queue)
then new element.
a) Verdadero
b) Falso

5) Es correcto el axioma:
frontq(enqueue(queue,element)) = if isempty(queue)
then element
else front(queue).
a) Verdadero
b) Falso

6) Cuando se implementa una cola como arreglo, cul de las siguientes operaciones
es relativamente lenta?
a) Agregar un elemento a la cola
b) Encontrar el frente de la cola
c) Encontrar el ltimo elemento de la cola
d) Eliminar un elemento de la cola

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 138

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

7) Si se quiere determinar si una cola est llena, simplemente se debe chequear si la


cola no est vaca.
a) Verdadero
b) Falso

8) En cules de las siguientes situaciones sern usadas las colas como una opcin
adecuada de estructura de datos?
a) Controlar los clientes que esperan al frente de un mostrador de pago en
efectivo en una tienda por departamento
b) Administrar el trfico de una red
c) Describir la estructura organizacional de una compaa
d) Todas las anteriores

9) Cuando una cola se implementa como arreglo circular, no es difcil diferenciar


entre un cola vaca y llena.
a) Verdadero
b) Falso

10) Para cules de las siguientes aplicaciones, se utiliza una cola como estructura de
datos?
a) Imprimir documentos por la red a travs de una impresora comn
b) Mantener una lista de aviones que vuelan fuera de una ciudad
c) Determinar el nmero de personas al frente del mostrador de pagos de una
tienda por departamentos
d) Todas las anteriores

Unidad 6: Colas Libro 1: Estructura de Datos y Algoritmos 139

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Respuestas a la Unidad 6: Examen de Autoevaluacin


1) a
2) d
3) c
4) b
5) a
6) d
7) b
8) a y b
9) b
10) a y c

Libro 1: Estructura de Datos y Algoritmos Unidad 6: Colas 140

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser preproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 7: Laboratorio de Colas


Objetivos de Aprendizaje
Al final de esta unidad, usted ser capaz de:
Aplicar los conceptos de TDA colas en cualquier problema.
Crear diferentes tipos de colas.
Implementar operaciones sobre colas.

Libro 1: Estructura de Datos y Algoritmos Unidad 7: Laboratorio de Colas 141

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejercicio de Laboratorio
Considere una cola FIFO que contenga enteros. Escribir:
Funciones adecuadas para las operaciones sobre colas.
Fragmentos de programa para llevar a cabo partes especficas de los
requerimientos.
Un programa completo C que realice las siguientes tareas:
1) Tomar como entrada los diferentes enteros posibles que deben formar la cola inicial.
Tomar tantas entradas como sea posible y crear la lista inicial hasta que el usuario
ingrese el valor -9999 para terminar el ingreso. Este valor no debe ser parte de la
lista.
2) Implementar las operaciones comunes sobre colas, como NewQ (crea una cola
nueva vaca), InsertQ (inserta un elemento al final de la cola), RemoveQ (retira un
elemento del frente de la cola) y isEmptyQ (que devuelve TRUE si la cola est
vaca y FALSE en caso contrario). Escribir fragmentos en main() que muestren la
invocacin de estas operaciones con salidas relevantes.
3) Algunas personas se salen de las colas en la vida real. Este fenmeno se
denomina balking de cola. Escribir una funcin llamada balkval(x), que
encuentra el primer elemento de la cola que es x, y lo retira de la cola. Invocar a
esta funcin y mostrar la cola resultante para ilustrar el trabajo de esta funcin.
Recomendaciones:
Escribir todas las funciones de cola utilizando la implementacin como lista
enlazada.
En la funcin main, obtener la entrada de los usuarios.
Realizar la validacin de la entrada. No aceptar enteros negativos.
Garantizar que 9999 no sea parte de la cola.
Hacer un programa tan modular como sea posible.
Tareas Opcionales:

Las siguientes tres preguntas son opcionales.


1) Escribir una funcin llamada balkpos(p), que toma como entrada la posicin del
elemento al frente de la cola y retira el elemento de la cola. Invocar esta funcin y
mostrar la cola resultante para ilustrar el trabajo de la misma.
2) Fusionar dos colas distintas con mergeQ(q1,q2), tal que q2 est fusionada al final
de q1. En otras palabras, el elemento front de q2 seguir al elemento rear de q1.
Invocar esta funcin y mostrar la cola resultante para ilustrar el trabajo de la
misma.
3) Escribir funciones separadas para los ejercicios opcionales.

Unidad 7: Laboratorio de Colas Libro 1: Estructura de Datos y Algoritmos 142

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Volumen 2: Estructuras de Datos


Avanzadas

Libro 1: Estructura de Datos y Algoritmos Unidad 7: Laboratorio de Colas 143

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 1: Grafos
Objetivos del Aprendizaje
Al final de esta unidad, usted debe ser capaz de:
Definir grafos dirigidos y no dirigidos.
Explicar las propiedades de los grafos no dirigidos.
Definir trminos asociados con grafos.
Discutir la representacin de un grafo como un conjunto, una tabla de
adyacencia y una lista de adyacencia.
Describir las aplicaciones de los grafos.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 145

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

1. Introduccin
Los grafos, como estructuras matemticas, se usan en diferentes ambientes como la
qumica, ingeniera elctrica, informtica, sociologa y geografa, as como, en modelos
matemticos. Por ejemplo, las vas de trenes, caminos o conexiones areas entre
ciudades pueden ser representadas por un grafo. En un circuito lgico digital, los
componentes y las conexiones entre estos pueden ser representados por un grafo. Las
lneas de autoridad y responsabilidad entre las personas en una compaa pueden ser
representadas por un grafo. En forma similar, existen muchos ejemplos de uso de
grafos en diversas reas de aplicacin. Otras aplicaciones de grafos se discuten en la
Unidad 6: Aplicacin de Grafos.

En esta unidad se tratarn slo los conceptos fundamentales de grafos y como estos
pueden ser representados en una computadora. No se discutir ninguna operacin o
implementacin de grafos.

A continuacin se aprendern algunos conceptos preliminares acerca de los grafos.

2. Preliminares de Grafos
Un grafo est compuesto de un conjunto de vrtices y un conjunto de aristas. Los
vrtices y aristas tambin se denominan nodos y arcos respectivamente. Una arista es
realmente un par de vrtices dado que conecta dos vrtices cualesquiera en un grafo.
Las Figuras 1.1(a) y 1.1 (b) muestran dos ejemplos de grafos.

Figura 1.1(a): Rutas Areas Parciales

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 146

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

La Figura 1.1(a) muestra un grafo de rutas areas parciales entre cinco ciudades de
Norteamrica. En el grafo que conecta las ciudades, una arista entre Cincinnati y
Florida indica que est disponible una ruta directa. Dado que no hay una arista
directa entre Cincinnati y Puerto Rico, no existe una ruta de vuelo disponible
directa entre las dos ciudades. Note que se puede ir desde Cincinnati a Florida y
luego a Puerto Rico.

A continuacin observe la Figura 1.1 (b).

Figura 1.1(b): Prerrequisitos para Cursos

La Figura 1.1(b) muestra un grafo de prerrequisitos para cursos.


En ambas figuras, slo han mostrado los vrtices del grafo con nombres. En el primer
grafo, las direcciones de las rutas areas no estn indicadas. No hay forma de saber si
la ruta area existe entre Cincinnati y Boston, Boston y Cincinnati o ambas.
Nuevamente, en el segundo grafo, el orden de prerrequisitos para los cursos no est
claro. Por ejemplo, no est claro si C es un prerrequisito para C++ o Linux Basics, o
ambos. Sin embargo, una pequea modificacin a estas representaciones de grafos
puede proporcionar la informacin requerida. A continuacin se aprender acerca de
cmo esta informacin es proporcionada en un grafo, en la Unidad 4 - Grafos Dirigidos.
Para entender ms acerca de aristas y vrtices de un grafo, considere el grafo que se
muestra en la Figura 1.2.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 147

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 1.2: Grafo G con Cuatro Vrtices

El grafo G, de la Figura 1.2, consiste de lo siguiente:


Un conjunto V, de vrtices, donde V = (p,q,r,s).
Un conjunto E, de aristas, donde E = (pq,pr,qr,rs,ss). Una arista se
escribe simblicamente como:
x = (p,q)
Donde x es una arista conectando los vrtices p y q.
Algunos trminos comunes que se usan relacionados a grafos son:
Incidir.
Yacer.
Estos trminos se comprendern an ms con la ayuda de la Figura 1.2.

Considere la arista x = (p,q).


El vrtice p se dice que es adyacente al vrtice q, dado que existe una arista
entre estos dos vrtices.
La arista x es incidente con los vrtices p y q, dado que conecta estos dos
vrtices.
Los vrtices p y q yacen en la arista x, dado que estn conectados por esta
arista.
Los grafos pueden ser clasificados como dirigidos y no dirigidos. A continuacin se
aprender ms acerca de los grafos no dirigidos.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 148

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

3. Grafos No Dirigidos
Un grafo no dirigido se define como un grafo donde los pares de vrtices estn
desordenados. Por desordenados, se entiende que las aristas en un grafo no dirigido no
tienen un vrtice origen ni un vrtice destino. Las Figuras 1.1(a), 1.1(b) y 1.2 son
ejemplos de grafos no dirigidos. En estos grafos, se muestra que una arista existe entre
un par de vrtices, pero no se muestra la direccin de la conexin. Se van a definir
algunos trminos bsicos usados en el contexto de grafos no dirigidos.

3.1 Adyacente:
Si existe una arista entre dos vrtices, por ejemplo, p y q, entonces se dice que son
vrtices adyacentes. En la Figura 1.2, se puede ver que los vrtices (p,q), (p,r),
(q,r) y (r,s) son adyacentes.

3.2 Camino:
Un camino es un conjunto de una secuencia de vrtices adyacentes distintos. En la
Figura 1.2, la secuencia de vrtices adyacentes distintos q,p,r,s forma un camino.
Los vrtices q y s no forman un camino. Un nodo puede tener un camino a s mismo.
En la Figura 1.2, el vrtice s tiene un camino a s mismo.

3.3 Ciclo:
Un ciclo se define como un camino que contiene un nmero n de vrtices, colocados de
forma que el vrtice 1 es adyacente al vrtice 2, el vrtice 2 es adyacente al vrtice 3, el
vrtice n-1 es adyacente al vrtice n y finalmente el vrtice n es adyacente al vrtice 1.
En la Figura 1.2, se puede ver que el camino consistente de los tres vrtices q, p, y r
forma un ciclo. Si se considera q como el vrtice 1, ste es adyacente al vrtice p, que
es adyacente al vrtice r. Finalmente, el vrtice r es adyacente al vrtice 1, que es q.

3.4 Grafo Conectado:


Un grafo conectado es aquel donde existe un camino de cualquier vrtice en el grafo
hacia cualquier otro vrtice. El grafo en la Figura 1.2 es un grafo conectado.

3.5 rbol Libre:


Un rbol libre es un grafo no dirigido que no tiene ciclos. El grafo de la Figura 1.3 es un
rbol libre.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 149

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 1.3: rbol Libre

4. Grafos Dirigidos
En las Figuras 1.1(a) y 1.1(b) no haba informacin acerca de la direccin de la ruta
area o del orden de los prerrequisitos para un curso. Usar un grafo cuyas aristas
indican una direccin ayuda a obtener esa informacin.

Un grafo dirigido es definido como aquel donde los pares de vrtices son ordenados.
Por ordenados, se entiende que cada arista en un grafo dirigido tiene un vrtice origen y
un vrtice destino. Es un grafo con un arco representando las aristas y una flecha
indicando la direccin. La Figura 1.4 es el mismo grafo mostrado en la Figura 1.1(b),
pero con direcciones.

Figura 1.4: Prerrequisitos para Cursos Grafo Dirigido

En la Figura 1.4, existe un camino dirigido entre el vrtice Linux Basics y C. El curso
que aparece al comienzo de la lnea dirigida es el prerrequisito para el curso al final de
la lnea dirigida. As, es evidente que Linux Basics es prerrequisito para C, C es
prerrequisito para C++, C++ es prerrequisito para Core Java y as sucesivamente.
Ahora que se tiene un claro entendimiento de los prerrequisitos para cada curso.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 150

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Al aadir direccin a las aristas en un grafo hace que ste sea un grafo dirigido. Algunas
de las observaciones que pueden hacerse de la Figura 1.4 son:
El curso Enterprise Java tiene dos prerrequisitos.
Para estudiar Enterprise Java, se debe haber cursado:
- Linux Basics.
- C.
- C++.
- Core Java.
- Web Programming I.
Los cursos Linux Basics y XML no tienen prerrequisitos.
Para estudiar WebSphere Commerce Suite, se debe estudiar primero todos los
otros cursos listados en la Figura.
Seguidamente, se explican las dos propiedades de un grafo dirigido con la ayuda de la
Figura 1.5.

Figura 1.5: Grafo Dirigido con Cuatro Vrtices

En un grafo dirigido todas las aristas en un camino tienen la misma direccin indicada
por las flechas. Tal camino se llama un camino dirigido.
Los caminos en la Figura 1.5 se listan a continuacin:
p,q
p,q,s
p,q,s,r
p,q,s,r,q
p,r
p,r,q
p,r,q,s
p,r,q,s,r
p,s

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 151

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

p,s,r
p,s,r,q
q,s
q,s,r
q,s,r,q
s,r
s,r,q
s,r,q,s
r,q
r,q,s
r,q,s,r
Cada arista en el camino tiene la misma direccin. Tome, por ejemplo, el camino p,q,s,
que tiene dos aristas llamadas p,q y q,s. Ambas aristas tiene la misma direccin.

En un grafo dirigido, todas las aristas en un ciclo deben tener la misma direccin. Los
ciclos en un grafo dirigido se denominan ciclos dirigidos.

Existen muchos ciclos en la Figura 1.5. Uno de ellos es q,s,r,q. Todas las aristas en
este ciclo, llamadas q,s; s,r, y r,q tienen la misma direccin.

5. Grafos y Estructuras de Datos


Nota: A partir de este punto, todas las referencias a 'grafo' implican un grafo dirigido.

A fin de poder usar los grafos en aplicaciones, se debe encontrar un mtodo para
representarlos como una estructura de datos. Se ha visto que los dos elementos de
datos importantes de los grafos son los vrtices y aristas. Los dos mtodos siguientes
se usan comnmente para representar un grafo como una estructura de datos:
Representacin en conjuntos.
Tablas de Adyacencia.
5.1 Representacin de Grafos en Conjuntos

Al comienzo de esta unidad, se defini un grafo como consistente de un conjunto de


vrtices y un conjunto de aristas. Se definieron los grafos en trminos de conjuntos.
Ahora, se ver si los grafos se pueden representar como un conjunto. Para representar
un grafo se necesita representar dos conjuntos:
Conjunto de vrtices.
Conjunto de pares de vrtices que representan aristas.
Un mtodo de representar los grafos usando conjuntos, es mantener dos conjuntos
diferentes, como ya se mencion anteriormente. Otro mtodo es tener slo un conjunto,
que, en efecto, proporciona la misma informacin que los dos conjuntos diferentes. La

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 152

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Figura 1.6 ser usada para ilustrar cmo pueden usarse los conjuntos para representar
grafos.

Figura 1.6: Grafo para Ilustrar la Representacin en Conjuntos

Primero se listarn los vrtices y las aristas del grafo de la Figura 1.6.

Vrtices
Cincinnati
New Jersey
New York
Boston
Aristas
Cincinnati, New Jersey
Cincinnati, New York
Cincinnati, Boston
New Jersey, New York
New Jersey, Boston
New York, New Jersey
New York, Boston
Boston, Cincinnati

5.1.1 Representar Grafos Usando Dos Conjuntos


En este mtodo de representacin de grafos, se crean dos conjuntos a saber:
vrtices y aristas, que guardan los vrtices y aristas listados anteriormente.
Seguidamente, se va a entender el uso de estos conjuntos con la ayuda de dos
operaciones.
Existencia de un vrtice: Primero, se buscar en el conjunto vrtices para
determinar si un vrtice existe o no en el grafo.
Asuma que el vrtice de entrada para el grafo en la Figura 1.6 es Florida.
Observe que no es un vrtice en el grafo, pues no es parte del conjunto
vrtices.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 153

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Existencia de un camino: Para encontrar un camino en un grafo se necesitan


dos vrtices como entrada, un vrtice origen y un vrtice destino. Usando los
valores de entrada y el conjunto aristas, se determinar si existe un camino
en el grafo.
Para el grafo en la Figura 1.6, si el vrtice origen es New York y el vrtice
destino es Cincinnati, entonces se puede encontrar si un camino existe
usando el conjunto aristas de la siguiente manera:
- Encontrar si existe una arista en el conjunto aristas que tenga a New
York como el primer vrtice en la entrada de aristas. Se encuentran dos
entradas en el conjunto aristas.
New York, New Jersey
New York, Boston
- Se sabe, viendo los pares de estas dos entradas, que no existe un camino
directo a Cincinnati desde New York. Considere el primer par, New York y
New Jersey. Este par representa un camino entre estos vrtices.
- Ahora considere New Jersey como el nuevo origen, sin cambiar el vrtice
destino. Se encuentran dos entradas para New Jersey como el primer vrtice
en la entrada de aristas.
New Jersey, New York
New Jersey, Boston
- An no se tiene un camino a Cincinnati. Por lo tanto, se considera la
primera de estas dos entradas para derivar el nuevo origen. Esto da como
resultado a New York como el nuevo origen. Se hace caso omiso de esto,
dado que el primer origen fue New York (en otras palabras, realmente se ha
encontrado un ciclo en este grafo!). A continuacin se considera la segunda
entrada con New Jersey como el primer vrtice, que da a Boston como el
nuevo vrtice origen.
- Usando Boston como el nuevo vrtice origen, slo se observa una entrada en
el conjunto aristas, que tiene un camino directo hacia Cincinnati, el
vrtice destino.
Se ha encontrado un camino entre New York y Cincinnati, a pesar que este
no es el camino ms corto. El camino ms corto desde New York a
Cincinnati es va Boston sin tocar New Jersey. La discusin sobre
encontrar el camino ms corto entre dos vrtices en un grafo, est ms all del
alcance de este curso.
Tambin es posible que quizs no exista un camino entre dos vrtices de
entrada. Usando los pasos anteriores, finalmente se agotaran todas las
entradas de aristas. Esto revelar que no existe un camino entre los dos
vrtices de entrada. Tambin es posible que, a veces, se necesite regresar al
paso anterior para tomar otra ruta. Una discusin de esto, est fuera del alcance
de este curso.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 154

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Otro mtodo de usar conjuntos para representar un grafo involucra usar slo un
conjunto, el cul, en efecto, proporciona la misma informacin que dos conjuntos
diferentes. A continuacin se discute cmo se usa este mtodo.

5.1.2 Representar Grafos Usando Un Conjunto

En este mtodo, se usan muchas instancias del conjunto aristas. Para cada vrtice
se tiene un conjunto aristas representado por separado. Para el grafo en la Figura
1.6, se tienen los siguientes conjuntos de aristas:
Vrtice Cincinnati
{Cincinnati-New Jersey, Cincinnati-New York,
Cincinnati-Boston}
Vrtice New Jersey
{New Jersey-New York, New Jersey-Boston}
Vrtice New York
{New York-New Jersey, New York-Boston}
Vrtice Boston
{Boston-Cincinnati}
Para encontrar si un vrtice existe, se debe determinar si existe un conjunto
aristas para el vrtice de entrada. Si existe, el vrtice es parte del grafo.
Para encontrar si un camino existe, se busca en el conjunto de aristas del
vrtice origen. De las entradas del conjunto del vrtice origen, se elige el vrtice
destino, que luego se convierte en el nuevo vrtice origen, igual a lo que se hizo
en el mtodo anterior. Estos pasos se repiten hasta que se encuentre que el
vrtice destino en uno de los conjuntos aristas, corresponde con el vrtice
destino original. Tambin es posible que se agoten todas las entradas del
conjunto de aristas sin encontrar un camino entre los dos vrtices de entrada.
Esto es similar al algoritmo presentado en el primer mtodo.
A veces un tercer conjunto, llamado el conjunto adyacente, tambin es considerado.
Este conjunto contiene los vrtices adyacentes a un vrtice en el grafo. Pueden existir
varias instancias del conjunto adyacente, uno para cada vrtice, similar a las varias
instancias del conjunto aristas descritas en este mtodo. Para el grafo en la Figura
1.6, los conjuntos adyacentes son:

Conjunto adyacente para el vrtice Cincinnati


{New Jersey, New York, Boston}
Conjunto adyacente para el vrtice New Jersey
{New York, Boston}
Conjunto adyacente para el vrtice New York

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 155

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

{New Jersey, Boston}


Conjunto adyacente para el vrtice Boston
Cincinnati}
Mediante el uso de los conjuntos adyacentes, se puede representar completamente
un grafo. Los conjuntos de aristas y los conjuntos adyacentes se pueden usar para
representar el mismo grafo. Para encontrar si un vrtice existe, se puede seguir el
mismo algoritmo que se us cuando se representaron los grafos usando un slo
conjunto. Para encontrar si un camino existe, se debe seleccionar una entrada
directamente desde los conjuntos adyacentes, dado que los conjuntos slo contienen
el vrtice adyacente.

Como se mencion antes, no se discutir la implementacin de conjuntos. Los grafos


pueden ser implementados como conjuntos, si el lenguaje de programacin soporta
conjuntos como un tipo de datos. C no soporta conjuntos, mientras que Pascal y Modula
2 si lo hacen.

Ahora se explicar el uso de una tabla de adyacencia para representar un grafo.

5.2 Tablas y Listas de Adyacencia

Dado que muchos lenguajes de programacin modernos no ofrecen conjuntos como un


tipo de dato, se pueden representar un conjunto en dos formas, ya sea como una tabla
de adyacencia o como una lista de adyacencia. A continuacin se presenta la forma de
lograr esto desde el punto de vista conceptual.

5.2.1 Representar Grafos Usando Tablas de Adyacencia


Se ha visto como los conjuntos de adyacentes se pueden usar para representar un
grafo. La informacin presentada en los conjuntos adyacentes se puede capturar en
una matriz bidimensional, las filas representando los vrtices y las columnas
representando los vrtices adyacentes. Las celdas en la matriz contendrn 0 1. Aqu,
el 1 representa la existencia de un vrtice adyacente. La Tabla 1.1 muestra la tabla de
adyacencia, tambin conocida como la matriz de adyacencia, para el grafo de la Figura
1.6.

Vrtice Cincinnati New Jersey New York Boston

Cincinnati 0 1 1 1

New Jersey 0 0 1 1

New York 0 1 0 1

Boston 1 0 0 0

Tabla 1.1: Matriz Adyacente para el Grafo en la Figura 1.6

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 156

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Dada la matriz en la Tabla 1.1, se puede observar si un vrtice existe buscando en


cualquiera de los valores de las filas o columnas. Para encontrar si existe un camino, se
sigue el algoritmo usado en el mtodo, empleando slo un conjunto. En vez de obtener
el vrtice origen en cada paso, se deriva buscando el valor de la celda. Si la celda
contiene un 1, entonces se sabe que existe un camino entre los dos vrtices.

5.2.2 Representar Grafos Usando Listas de Adyacencia


Tambin se puede representar un conjunto como una lista de sus elementos. Cuando
se quiere representar grafos se necesita tener una lista de vrtices y para cada vrtice,
una lista de sus vrtices adyacentes. Se puede pensar en implementar ambas listas de
vrtices y la lista de adyacencia, usando listas enlazadas.

Para entender el uso de las listas enlazadas como mecanismo de implementacin para
listas de adyacencia, considere el grafo dirigido que se muestra en la Figura 1.7.

Figura 1.7: Grafo para Ilustrar una Lista de Adyacencia

Este grafo dirigido tiene cuatro vrtices y siete aristas.

Los cuatro vrtices del grafo son:


p
q
r
s
Las siete aristas del grafo son:
pq
ps
qs
qr
sq
sr

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 157

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

rp
Para representar la lista de adyacencia usando una lista enlazada, se deben tener dos
listas enlazadas conectadas entre s.

La Figura 1.8 tiene cinco listas enlazadas. Una lista se usa para representar los vrtices
en el grafo dirigido, llamados p, q, r y s. Se denomina esta lista, la lista de vrtices con
cuatro nodos. Cada nodo en la lista de vrtices representa un vrtice del grafo. Las
otras cuatro listas proceden de cada uno de los cuatro nodos de la lista de vrtices. Los
nodos en las cuatro listas enlazadas representan las aristas que proceden de cada
vrtice. Para simplificar las cosas, se muestran vrtices y aristas en la parte de
informacin de los nodos de las cinco listas enlazadas.

Figura 1.8: Representacin Grfica de una Lista de Adyacencia Usando Listas Enlazadas

Cada nodo en la lista enlazada que representa a los vrtices, p, q, r y s, tiene lo


siguiente:
Un puntero al primer nodo de la lista enlazada, representando las aristas en que
participa el vrtice (Ej. El nodo conteniendo a p apunta a la lista enlazada que
representa todas las aristas que empiezan con p, esto es, pq y ps).
Un puntero al siguiente nodo en su lista.
Cada nodo en la lista enlazada que representa las aristas, pq, qs, rp y sq, tiene lo
siguiente:
Un puntero al vrtice final de la arista (el nodo representando la arista pq apunta
al vrtice q).
Un puntero a la siguiente arista en su lista.
El siguiente algoritmo realiza un recorrido simple del grafo:

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 158

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

El nodo cabecera ser reconocido como graph. Dado que es el nodo cabecera y tiene
un vrtice inicial p, de tal forma que se puede llegar a lo siguiente:
Al visitar p. Desde p se puede visitar q, desde q se puede visitar r, y desde r
se puede visitar s. Esto completa el recorrido de la lista enlazada que representa
los vrtices.
Al visitar p. Desde p se puede visitar pq, y desde pq se puede visitar ps. Esto
da todas las aristas que empiezan desde p.
Al visitar p. Desde p se puede visitar pq. Desde pq se puede visitar q y desde q
se puede visitar qr. Desde qr se puede visitar r y desde r se puede visitar rp.
El primer vrtice de pq es el vrtice final de rp que fue visitado finalmente. Esto
completa un ciclo en el grafo dirigido.
As, es fcil derivar estas cosas acerca de un grafo cuando las listas de adyacencia se
representan usando listas enlazadas.

Ahora se discutir brevemente unas cuantas aplicaciones que involucran grafos.

6. Aplicaciones de Grafos
6.1 Representacin de una Red de Caminos
Los grafos se pueden usar para representar redes de caminos. En general, se pueden
usar para representar cualquier ruta de viaje, ya sea por tierra, mar o aire. Los
algoritmos de grafos se pueden usar para determinar si un camino de viaje existe desde
un origen a un destino. Adems, se puede calcular el camino ms corto desde un origen
a un destino usando algoritmos de grafos.

6.2 Diagramas de flujo


Se pueden usar para representar diagramas de flujo o tambin programas. Esto tiene
varias aplicaciones, como encontrar la complejidad de un programa y generar casos de
prueba.

6.3 Implementar Autmatas

Se pueden usar para representar e implementar autmatas. Esto tiene un nmero de


aplicaciones en la construccin de compiladores y otras reas de la informtica.

6.4 Algoritmos de Grafos


Una de las muchas aplicaciones de grafos son los algoritmos de grafos. Los algoritmos
de grafos son aquellos que proporcionan soluciones para encontrar caminos, vrtices
adyacentes, aristas, etc. en un grafo. Algunos de los principales son:
Alcance.
Camino ms corto.
rbol de mnima expansin.
El camino de menor costo a travs de todos los nodos en un grafo.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 159

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

6.5 Problemas de Optimizacin a travs de PERT/CPM

Los grafos tienen excelente aplicabilidad en resolver problemas de optimizacin. Los


grafos representan las redes usadas en la Tcnica de Evaluacin y Revisin de
Programa (Program Evaluation and Review Technique - PERT) y el Mtodo del Camino
Crtico (Critical Path Method - CPM). PERT se usa en la planificacin, evaluacin y
control de proyectos. CPM ayuda a identificar los cuellos de botella potenciales en un
proyecto.

6.6 Mapas y Bases de Datos Geogrficas

Los grafos se pueden usar para representar mapas y entidades en bases de datos
geogrficas. Sus aplicaciones se extienden a sistemas de informacin geogrficos y
cartografa.

6.7 Diseo de Dispositivos de Integracin a Gran Escala (VLSI)


Los grafos y la teora de grafos se han usado en el rea del diseo VLSI. La
optimizacin de circuitos, el uso de componentes digitales y espacio de chips son
algunas de las reas en los que se usan grafos.

6.8 Reconocimiento de Caracteres y Correspondencia de Huellas


Dactilares
Las aplicaciones de grafos se extienden al reconocimiento de caracteres. Esto tiene
aplicacin en la identificacin electrnica de firmas. El reconocimiento ptico de
caracteres ayuda a convertir documentos escritos a mano a un formato de texto que
puede ser almacenado electrnicamente. Los grafos tambin tienen mucha aplicacin
en reconocimiento de huellas dactilares.

6.9 Estructuras Qumicas

Las estructuras qumicas como molculas bidimensionales se pueden representar como


grafos. Los nodos pueden representar los tomos, mientras que los enlaces entre ellos
pueden representarse por aristas. Puede construirse un nmero de aplicaciones sobre
estos, tales como identificacin de anillos y estructuras isomrficas.

6.10 Modelamiento Biolgico

Los grafos tienen varias aplicaciones en el modelamiento biolgico. Varias estructuras


que ocurren en biologa se pueden representar usando grafos. Existe un nmero de
aplicaciones en el rea de la ingeniera gentica, bio-informtica y biologa molecular.
Tambin se pueden usar en el rea de secuencia del ADN.

6.11 Reconocimiento de Imgenes y Patrones

Los grafos se han usados en el rea de reconocimiento de imgenes y patrones. Su


aplicabilidad va ms all del reconocimiento tradicional de imgenes hasta reas de
visin de computadoras.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 160

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

6.12 Conceptos de Modelamiento Orientado a Objetos

Los grafos tienen aplicaciones en el rea de anlisis y diseo orientados a objetos. Las
herramientas UML (Unified Modeling Language) y varios CASE (Computer Aided
Software Engineering) que soportan mtodos orientados a objetos hacen uso de grafos.

6.13 Laberintos y Deteccin de Rutas


Los grafos se pueden usar para resolver problemas relativos a laberintos.
Indirectamente, los grafos tambin se usan en problemas de deteccin de rutas,
especialmente en juegos.

6.14 Deteccin de Semejanza


Los grafos se pueden usar en forma efectiva en la deteccin de semejanza. Tienen un
amplio rango de aplicaciones, desde ayudar a detectar fraudes de impuestos hasta
detectar actividades de lavado de dinero o crimen organizado.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 161

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que Ud. ha completado esta unidad, debe ser capaz de:
Definir grafos dirigidos y no dirigidos.
Explicar las propiedades de los grafos no dirigidos.
Definir los trminos asociados con grafos.
Discutir la representacin de un grafo como un conjunto, una matriz de
adyacencia y una lista de adyacencia.
Describir las aplicaciones de los grafos.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 162

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 1: Examen de Autoevaluacin


1) Un grafo tiene:
a) Slo vrtices.
b) Slo aristas.
c) Tanto aristas como vrtices.
d) Ninguna de las anteriores.

2) Qu representa k = (diversin,feliz)?
a) Un grafo.
b) Un ciclo en un grafo.
c) Un vrtice en un grafo.
d) Una arista en un grafo.

3) Si e = (a,b), entonces a y b se dicen que yacen en e. En este caso, e es


_______ a y b.
a) Adyacente a.
b) Incidente con.

4) Considere un camino conteniendo al menos tres vrtices colocados de forma que


el ltimo vrtice en el camino es adyacente al primero.Cmo se llama tal camino?
a) Grafo.
b) Ciclo.

5) Cul de los siguientes es un grafo no dirigido conectado sin ciclos?


a) rbol libre.
b) Heap.

6) En un grafo dirigido, los vrtices a y b pueden tener caminos a cada uno.


a) Verdadero.
b) Falso.

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 163

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

7) El siguiente grafo tiene un ciclo.

a) Verdadero.
b) Falso.

8) Cules de los siguientes se pueden usar para representar un grafo como una
estructura de datos?
a) Conjuntos.
b) Matriz de adyacencia.
c) Lista de adyacencia.
d) Slo (a) y (c).

9) En el mtodo donde se tienen conjuntos de vrtices y aristas. En cul de los


siguientes se busca para determinar si un camino existe?
a) Vrtices.
b) Adyacente.
c) Aristas.
d) Todos los anteriores

10) En la matriz de adyacencia, las filas representan los vrtices adyacentes de un


vrtice.
a) Verdadero.
b) Falso.

Unidad 1: Grafos Libro 1: Estructura de Datos y Algoritmos 164

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Respuestas a la Unidad 1: Examen de Autoevaluacin


1) c
2) d
3) b
4) b
5) a
6) a
7) b
8) a, b y c
9) c
10) b

Libro 1: Estructura de Datos y Algoritmos Unidad 1: Grafos 165

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 2: rboles
Objetivos del Aprendizaje
Al final de esta unidad, Ud. debe ser capaz de:
Definir un rbol como una estructura de datos.
Discutir rboles binarios, rboles de bsqueda binaria y rboles en general.
Explicar los tres mtodos de recorrido para un rbol binario.
Definir un heap.
Distinguir entre un heap mnimo y un heap mximo.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 167

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

1. Introduccin
Se han estudiado las listas, pilas, colas y grafos que se pueden usar como estructuras
de datos en aplicaciones a travs de implementaciones de arreglos o listas enlazadas.
En esta unidad, se aprendern a usar los rboles como estructuras de datos. Se
estudiarn los rboles binarios y cmo estos pueden extenderse en un rbol general.
Tambin se discute un tipo especial de rbol binario llamado heap.

2. rboles Generales
Un rbol general es aquel en que un nodo puede tener cero uno o ms de dos
subrboles. Un ejemplo de tal rbol es el 'rbol genealgico', que describe la genealoga
y estructura de una familia. Los rboles generales se usan en diversas reas de trabajo,
tales como, en matemticas y en ingeniera. En la informtica, los rboles generales se
usan para representar la estructura sintctica de programas fuentes en compiladores y
en organizar la informacin en las bases de datos.

Las caractersticas de un rbol general son:


Puede tener slo un nodo raz.
Es llamado un rbol nulo cuando no existen nodos.
Puede tener cero, uno o ms subrboles procediendo desde cualquier nodo del
rbol.
Un ejemplo de un rbol general se presenta en la Figura 2.10.

Libro: Estructura de Datos y Algoritmos

Estructura de Estructura Bsquedas y


Datos de Datos Algoritmos de
Simples Avanzadas Ordenamiento

Unidad 1: Unidad 2: Unidad 3:


Grafos rboles Tablas
Y Hash
Tablas Hash

Unidad 1: Unidad 2: Unidad 3: Unidad 4:


Unidad 1: Unidad 2: Unidad 3: Unidad 4: Unidad 5: Unidad 6: Unidad 7:
Algoritmos Lab. Algoritmos Lab.
Estructura Listas Lab. Pilas Lab. Colas Lab.
de Algoritmos de Algoritmos
de Enlazadas Listas Pilas Colas
Bsqueda de Ordenamiento de
Datos Enlazadas
Bsqueda Ordenamiento
Simples

Figura 2.10: rbol General

En el caso de un rbol binario, se habla acerca de slo dos hijos, el hijo izquierdo y el
hijo derecho. En el caso de un rbol general, se habla acerca del hijo mayor y el hijo

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 168

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

menor. Todos los hijos restantes entre el hijo mayor y menor son conocidos como otros
hijos del nodo padre.

Las operaciones realizadas en un rbol binario tambin son vlidas en un rbol general.
Un nodo puede ser insertado o eliminado, un elemento puede ser buscado y el rbol
puede ser recorrido. Pueden existir muchas otras operaciones especficas para un rbol
general. No se darn mayores detalles al respecto en este curso.

3. rboles Binarios
Normalmente, cuando se organiza una coleccin de elementos relacionados, el orden
jerrquico de los elementos est basado en un conjunto de sus atributos. Un rbol es
una opcin natural para representar el ordenamiento jerrquico.
Un rbol puede ser definido como una coleccin de nodos representando un
ordenamiento jerrquico. El ordenamiento jerrquico puede estar basado en la
informacin presente en los nodos. Un buen ejemplo de ordenamiento jerrquico es la
estructura de directorios del sistema operativo Linux.
Los nodos son los elementos de un rbol y guardan informacin. Los nodos pueden
guardar informacin de cualquier tipo de datos, desde tipos simples de datos como
enteros, reales hasta tipos estructurados como arreglos, pilas, colas y listas. Cada rbol
tiene un nodo raz. Un nodo raz es el primer nodo e indica el inicio de un rbol.
Usando esta definicin bsica de un rbol y un nodo, se va a definir un rbol binario.
Un rbol binario es un rbol en donde cada nodo puede tener cero, uno o dos hijos.
Cuando un nodo tiene 1 2 hijos, los nodos hijos en s mismos son rboles binarios,
dado que pueden tener tambin sus propios hijos. Por ello, los hijos de un rbol binario
tambin son conocidos como subrboles. La Figura 2.1 ilustra un rbol binario.

Figura 2.1: rbol Binario

Un rbol binario puede tener cero, uno o dos subrboles desde un nodo raz. Esto
implica que alguno o ambos subrboles pueden estar vacos. Se puede decir que un
rbol binario tiene las siguientes caractersticas:

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 169

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Un rbol binario puede tener slo un nodo raz.


Un rbol binario en el que no existe ningn nodo se llama un rbol nulo.
Un rbol binario puede tener cero, uno o dos subrboles desde cualquier nodo
del rbol.
Considere un rbol llamado Treex con el nodo raz Rootx y otro rbol llamado Treey
con el nodo raz Rooty. Adems, considere un nico nodo raz llamado The Root para
un tercer rbol llamado The Tree. Por definicin, este tambin es un rbol por s solo.
Ahora, se puede crear un nuevo rbol llamado Another Tree uniendo Treex y Treey
de tal forma que los nodos Rootx y Rooty estn conectados al nodo llamado The
Root. The Root es la raz del rbol recin formado. Tambin es llamado el nodo padre
de los nodos Rootx y Rooty. Los nodos Rootx y Rooty son llamados hijos del nodo
The Root. Esto se muestra en la Figura 2.2.

Figura 2.2: Unin de Tres rboles Binarios

Otro ejemplo de un rbol binario se presenta en la Figura 2.3 donde la raz no tiene un
subrbol izquierdo.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 170

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 2.3: rbol Binario sin Subrbol izquierdo

Se van a aprender algunas terminologas asociadas con un rbol binario, con la ayuda
de las Figuras 2.2 y 2.3.
Padre: Es aquel nodo que tiene al menos un hijo. Rooty es el padre de Y1 y Y2
en la Figura 2.2.
Hijo Izquierdo: Es aquel nodo o hijo que se ramifica a la izquierda desde un
nodo padre. Y1 es el hijo izquierdo de Rooty en la Figura 2.2. La Figura 2.3 no
tiene ningn hijo izquierdo.
Hijo Derecho: Es aquel nodo o hijo que se ramifica a la derecha desde un nodo
padre. Y2 es el hijo derecho de Rooty en la Figura 2.2.
Hoja: Es aquel nodo sin hijos. X1, X2, Y1, y Y2 de la Figura 2.2, y X4 de la Figura
2.3 son nodos hojas.
Nivel de un nodo: El nivel de un nodo se refiere al nivel en que existe el nodo
en el ordenamiento jerrquico. Este se denota por un nmero. Al nodo raz se le
asigna 0. A los hijos de la raz se les asigna 1. As, en un rbol, el nivel de cada
nodo se representa por el nivel de su padre ms uno. En la Figura 2.3, el nodo
X1 est en nivel 0, X2 est en nivel 1, X3 est en nivel 2, y X4 est en nivel 3.
Arista: Es la conexin entre el padre y sus hijos. En la Figura 2.3, la lnea
mostrada entre X1 y X2 es una arista.
Camino: Es una secuencia de aristas consecutivas. En la Figura 2.2, la
secuencia de nodos - The Root, Rootx, X1 - es un camino.
Longitud de camino: La longitud del camino es uno menos que el nmero de
nodos en el camino. La longitud de un camino puede ser cero. En la Figura 2.2,
la longitud del camino The Root, Rootx, X1, es dos.
Altura del rbol: La altura de un rbol denota el nmero mximo de nodos
desde la raz hasta la menor hoja en un rbol. Tambin se conoce como la
profundidad del rbol. La altura del rbol en la Figura 2.2 es tres y en la Figura
2.3 es cuatro.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 171

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

A continuacin se discute cmo un rbol binario se puede representar en C. Se puede


pensar en un rbol binario como una lista enlazada. Los enlaces se pueden mantener
en un rbol binario como se muestra a continuacin:
typedef int Tipo_elemento;
typedef struct Nodo_ArbolBinario {
Tipo_elemento elemento;
struct Nodo_ArbolBinario *izquierda;
struct Nodo_ArbolBinario *derecha;
} Tipo_ArbolBinario;
La definicin de un nodo para un rbol binario recuerda a la de un nodo de lista
enlazada. El nodo de rbol binario tiene dos punteros. Un valor NULL en cualquiera de
estas variables puntero indica que el subrbol es NULL.

Las operaciones tpicas en un rbol binario son la insercin y eliminacin de un nodo, la


bsqueda de un elemento y el recorrido del rbol. La nica implementacin que se
discutir en esta unidad es el recorrido de un rbol binario.

4. Recorrido de rboles
El recorrido involucra visitar cada nodo en el rbol. Los nodos pueden ser visitados
usando cualquiera de estas tres clases de recorridos: recorrido preorden, recorrido
inorden y recorrido postorden. Esto es similar a las notaciones prefija, infija y postfija
para representar expresiones que se aprendieron en el Volumen 1, Unidad 4:
Estructuras de Datos Simples, Pilas.

Los nodos de un rbol binario se listan usando cualquiera de los mtodos de recorrido.
Los tres mtodos de recorrido que se realizan en un rbol binario se dan a continuacin:
Recorrido Preorden
- Visitar el nodo raz.
- Visitar el nodo izquierdo.
- Visitar el nodo derecho.
Recorrido Inorden
- Visitar el nodo izquierdo.
- Visitar el nodo raz.
- Visitar el nodo derecho.
Recorrido Postorden
- Visitar el nodo izquierdo.
- Visitar el nodo derecho.
- Visitar el nodo raz.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 172

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

En los tres mtodos de recorrido, cuando un subrbol es visitado, la regla se aplica


nuevamente. Se va entender como la regla se aplica nuevamente en un subrbol con la
ayuda de la Figura 2.4, que muestra un rbol binario simple de altura cuatro.

Figura 2.4: Recorridos de un rbol binario

En la Figura 2.4, existen dos subrboles cuyas races son b y e. Cuando se visitan
estos subrboles, se aplica nuevamente las reglas del recorrido.
A continuacin se presentan ejemplos de los recorridos preorden, inorden y postorden.
El rbol ejemplo usado para estos listados es el rbol de la Figura 2.4.

4.1 Listado en Preorden:


a b d e f c
Se obtiene el listado en preorden cuando la regla de recorrido preorden (raz,
izquierda, derecha) se aplica como se muestra a continuacin:
raz (a) // Toma el valor - a
izquierdo (b) // Tiene un subrbol, guarda valor para despus
raz (b) // Toma el valor - b
izquierdo (d) // No es un subrbol, toma el valor - d
derecho (e) // Tiene un subrbol, guarda valor para
despus
raz (e) // Toma valor - e
izquierdo (f) // No es un subrbol, toma el valor - f

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 173

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

derecho (c) // No es un subrbol, toma el valor - c


En el ejemplo anterior, el listado en preorden es a b d e f c. Al visitar el nodo b se
observa que tiene subrboles no vacos. Se aplica nuevamente la regla, tome el valor
en la raz y muvase a su nodo izquierdo, que es d. El Nodo d no tiene subrboles, y
por lo tanto, se toma directamente el valor. De esta forma, es posible visitar todos los
nodos en un rbol binario y obtener los valores en los nodos. Se nota que cuando se
alcanza la raz, se toma el valor aunque tenga un subrbol. Esto se debe a que la regla
de recorrido preorden establece raz, izquierda, derecha.

4.2 Listado en Inorden:


d b f e a c
Usando la regla de recorrido inorden (izquierda, raz, derecha), se obtiene el
listado en inorden como sigue:
raz (a) // Tiene subrboles, guarda valor para despus
izquierdo (b) // Tiene subrboles, guarda valor para despus
izquierdo (d) // No tiene subrboles, toma el valor d
raz (b) // Se mueve a su raz (b), toma el valor b
derecho (e) // Tiene un subrbol, guarda valor para despus
izquierdo (f)// No tiene subrboles, toma el valor f
raz (e)// Se mueve a su raz (e), sin subrbol derecho
// Toma el valor e
// Se mueve a su raz (b), valor ya tomado
raz(a) // Se mueve a su raz (a), toma el valor a
derecho (c) // No tiene subrboles, toma el valor c
En el recorrido preorden se toma el valor de la raz conforme se va moviendo en el rbol
binario. En el recorrido inorden, se guarda el valor y se toma cuando se llega a la raz
luego de visitar el nodo izquierdo. Si el nodo izquierdo tiene subrboles, entonces se
siguen visitando los nodos usando la regla de recorrido inorden.

4.3 Listado en Postorden:


d f e b c a
Ahora se buscar llegar al listado en postorden usando la regla de recorrido postorden
(izquierda, derecha, raz).
raz (a) // Tiene subrboles, guardar valor para despus
izquierdo (b) // Tiene subrboles, guardar valor para despus
izquierdo (d) // No subrbols, take value d
// No puede tomarse valor de la raz, pues el
// subrbol derecho no se ha recorrido an
derecho (e) // Tiene un subrbol,guardar valor para despus

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 174

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

izquierdo (f) // No tiene subrboles, tomar el valor f


// Se mueve a su raz(e), sin subrbol derecho
// Toma el valor e
// Se mueve a su raz (b), toma el valor b
// Se mueve a su raz(a),tiene subrbol derecho
derecho (c) // No tiene subrboles, tomar el valor c
// Se mueve a su raz(a), toma el valor - a
Aqu, nuevamente se observa que el listado en postorden se logra guardando valores
cuando una raz se alcanza conforme se sigue la regla izquierda, derecha, raz.

Pero si el rbol binario tiene un slo nodo, el rbol se considera que est preorden,
inorden y postorden.

A continuacin se va a escribir el cdigo C para los tres mtodos de recorrido.


Nota: En los tres mtodos se guarda el valor para ser tomado luego. La mejor eleccin
de un algoritmo, en tales casos es un algoritmo recursivo, a continuacin se presentan
los tres mtodos de recorrido usando funciones recursivas en C.

Preorden:

El cdigo C empieza aqu


void preOrder(Tipo_ArbolBinario *nodo) {
if (nodo != NULL) {
printf("%d\n", nodo->elemento);
preOrder(nodo->izquierdo);
preOrder(nodo->derecho);
}
}
El cdigo C termina aqu

Siguiendo la regla de recorrido preorden, la sentencia printf denota la visita del nodo
raz, seguida por una llamada a preOrder con el nodo izquierdo. Esto es seguido por
una llamada a preOrder con el nodo derecho. Las llamadas a preOrder aplicarn
nuevamente la regla, imprimiendo el valor de la raz y haciendo llamadas a preOrder
con los nodos izquierdo y derecho.

Inorden:

El cdigo C empieza aqu


void inOrder(Tipo_ArbolBinario *nodo) {
if (nodo != NULL) {

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 175

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

inOrder(nodo->izquierdo);
printf("%d\n", nodo->elemento);
inOrder(nodo->derecho);
}
}
El cdigo C termina aqu

En esta funcin, primero se hace una llamada a inOrder con el nodo izquierdo,
luego se imprime el valor de la raz seguido por una llamada a inOrder con el nodo
derecho.

Postorden:

El cdigo C empieza aqu


void postOrder(Tipo_ArbolBinario *nodo) {
if (node != NULL) {
postOrder(nodo->izquierdo);
postOrder(nodo->derecho);
printf("%d\n", nodo->elemento);
}
}
El cdigo C termina aqu

La funcin postOrder hace llamadas a s misma, primero con el nodo izquierdo y


luego con el nodo derecho. Al final, imprime el valor en la raz. Esto est de acuerdo
con la regla izquierda, derecha, raz.

En las tres funciones, si se reemplaza la sentencia printf con una sentencia if se


encuentra un elemento en el rbol usando el recorrido en preorden. La mayora de los
algoritmos de rbol usan una de estas formas de mtodos de recorrido.
if (nodo->elemento == elemento)
printf(Elemento encontrado\n);
En el caso de una lista enlazada, se tiene un nodo cabecera apuntando al inicio de una
lista. En forma similar para un rbol binario, un puntero externo conocido como rbol
apuntar a la raz del rbol binario. Este puntero externo ser pasado a estas tres
funciones, desde el cual el algoritmo recursivo toma el control.

Habiendo aprendido acerca de rboles binarios, se continuar aprendiendo acerca de


una clase especial de rbol binario llamado rbol de bsqueda binaria.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 176

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

5. rbol de Bsqueda Binaria


La bsqueda es una de las tareas ms comunes realizadas en cualquier esfuerzo de
desarrollo de software. Existen dos algoritmos, la bsqueda lineal y la bsqueda binaria,
que se pueden usar para buscar un elemento en una lista dada de elementos.

La bsqueda en una lista enlazada requiere moverse de un nodo a otro en la lista. Al


hacer eso, se est usando el algoritmo de bsqueda lineal. En el algoritmo de bsqueda
lineal se recorre cada elemento en la lista uno tras otro hasta que se encuentra el
elemento o se alcanza el final de la lista.

Otra forma de realizar una bsqueda es primero ordenar la lista de elementos. El


algoritmo de bsqueda binaria se aplica aqu. En el algoritmo de bsqueda binaria, la
lista ordenada es vista como dos listas, con un elemento en el medio de la lista tomado
como el elemento central. Si el elemento buscado es equivalente a este elemento
central, la bsqueda es un xito. Si no es igual al elemento central, entonces el
elemento puede encontrarse en la mitad superior o inferior de la lista. Si el elemento
buscado es menor que el elemento central, entonces se busca slo en la mitad inferior
de la lista, que ahora tiene un nuevo elemento central. Caso contrario, se busca en la
mitad superior de la lista, que tambin tiene un nuevo elemento central. Estos son los
fundamentos del algoritmo de bsqueda binaria. No se entrar por ahora en ms
detalles, dado que se estudiar el algoritmo de bsqueda binaria en la Unidad 3:
Estructuras de Datos y Algoritmos. Esta explicacin se da aqu para facilitar el trabajo
con los rboles de bsqueda binaria.

Un rbol binario construido con el propsito de bsqueda, basado en el algoritmo de


bsqueda binaria, es conocido como un rbol de bsqueda binaria. Un rbol de
bsqueda binaria es una forma especial de rbol binario. Algunas de las caractersticas
ms importantes de un rbol de bsqueda binaria son:
Si tiene un valor nulo para su raz, entonces es un rbol de bsqueda binaria
vaco.
Todos los elementos que ocurren antes (menores) el elemento en el nodo raz
estn en el subrbol izquierdo.
Todos los elementos que ocurren despus (mayores que) el elemento en el
nodo raz estn en el subrbol derecho.
El subrbol izquierdo tambin es un rbol de bsqueda binaria.
El subrbol derecho tambin es un rbol de bsqueda binaria.
Note que se han usado los operadores menor que y mayor que en las propiedades
anteriores. El elemento igual al nodo raz puede estar tanto a la izquierda como a la
derecha del nodo raz. De acuerdo a esto, se puede modificar las declaraciones dadas
para indicar 'menor o igual que' o 'mayor o igual que'. Slo una de ellas puede tomar la
clusula 'igual a'. Note que tanto el valor numrico o lexicogrfico (ordenar palabras
basados en el orden de las letras del alfabeto) de los elementos pueden ser
considerado para la comparacin.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 177

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

La Figura 2.5 ilustra un ejemplo de un rbol de bsqueda binaria.

Figura 2.5: rbol de Bsqueda Binaria

A partir de la Figura 2.5, se observa que el elemento raz es tal que todos los elementos
anteriores en orden del elemento raz estn en el subrbol izquierdo. El elemento raz
es 'Orlando, FL'. Todos los elementos en el subrbol izquierdo del rbol de bsqueda
binaria tienen valores que ocurren antes que el elemento de la raz. Como se usan
nombres de ciudades en la lista de elementos, se usa el mtodo del diccionario para
determinar los nombres que preceden a otros.

Todos los elementos que ocurren antes de 'Orlando, FL' estn en el subrbol
izquierdo. En forma similar, todos los elementos que ocurren despus de 'Orlando,
FL' en el orden estn en el subrbol derecho. Si observa en detalle la figura, tambin se
puede ver que cada subrbol tiene esta propiedad. Como ejemplo, observe 'Raleigh,
NC'. Note que todos los elementos que ocurren antes de 'Raleigh, NC' estn en su
subrbol izquierdo, mientras que todos los elementos que ocurren despus de
'Raleigh, NC' estn en su subrbol derecho.

Para buscar un elemento particular, primero se debe comparar el elemento con la raz
del rbol. Si el elemento que se busca no est en la raz, entonces se empieza a buscar
en el subrbol izquierdo o en el subrbol derecho, dependiendo si el elemento buscado
es menor o mayor que el elemento en la raz. Tpicamente, el operador igual a se
aplica tanto con el operador menor como con el mayor que. Asumiendo que el operador
igual a es aplicado con el mayor que, la bsqueda procede en el subrbol izquierdo de
la raz si el elemento buscado es menor que el elemento raz, y en el subrbol derecho
si el elemento buscado es mayor o igual que el elemento en la raz. La bsqueda
termina cuando el elemento es encontrado en el rbol. En caso contrario, la bsqueda
procede hasta el subrbol sea vaco.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 178

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Se va a entender cmo se usa el rbol de bsqueda binaria para realizar una bsqueda
con la ayuda de la Figura 2.5. Se asume que el elemento de bsqueda es
'Sacramento, CA'.
Se compara el elemento buscado con el valor en la raz, 'Orlando, FL'. Dado
que no es igual al valor en la raz, se verifica si es menor, mayor o igual que
'Orlando, FL'.
El elemento buscado es mayor que el valor en el nodo raz. Se moviliza hacia el
subrbol derecho de la raz. Esta se convierte en la nueva raz. El elemento
buscado se compara nuevamente con el valor en esta nueva raz, 'Raleigh,
NC'.
El elemento buscado no es igual a 'Raleigh, NC' y tambin es mayor que
'Raleigh, NC'. Ahora se moviliza a su subrbol derecho, que es 'San Diego,
CA'.
El elemento buscado no es igual al valor en la nueva raz. Pero se encuentra
que es menor que 'San Diego'. Ahora se mueve al subrbol izquierdo.
El elemento buscado es igual al valor en esta nueva raz, 'Sacramento, CA'.
As, la bsqueda es un xito.
Siguiendo el procedimiento anterior, cuando se alcanza un valor NULL al final, significa
que el elemento no est en el rbol de bsqueda binaria.

Una ventaja importante de usar rboles de bsqueda binaria es que resulta en


operaciones de bsqueda ms rpidas. Otra ventaja de construir un rbol de bsqueda
binaria est en derivar una lista ordenada de elementos. El mtodo de recorrido inorden
en un rbol binario siempre resulta en una lista ordenada de los elementos guardados
en el rbol binario. La lista inicial usada para crear el rbol binario de la Figura 2.5 se
presenta en la Figura 2.6.

Figura 2.6: Lista Inicial de Nombres de Ciudades

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 179

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Usando el recorrido inorden del rbol binario creado a partir de Initial List 1, se
obtiene la lista ordenada como se muestra en la Figura 2.7.

Figura 2.7: Lista Ordenada de Nombres de Ciudades

Si el conjunto de valores en Initial List 1 se dan en un orden diferente, como se


muestra en la Figura 2.8, se obtiene otro rbol de bsqueda binaria como se muestra en
la Figura 2.9.

Figura 2.8: Orden Inicial Diferente

Un rbol de bsqueda binaria se construye a partir de una lista de elementos en el


orden de aparicin de los elementos en la lista. As, se tiene que 'Orlando, FL' es el
nodo raz en la Figura 2.5 y 'Madison, WI' es el nodo raz en la Figura 2.9. La

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 180

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

construccin del rbol con el resto de los nodos sigue los mismos principios usados
para la bsqueda. Si el elemento a ser aadido al rbol de bsqueda es menor que la
raz, entonces se aade a la izquierda de la raz, caso contrario se aade a la derecha
de la raz. Esto se repite para todos los elementos en la lista.

Se observa que el rbol de bsqueda binaria presentado en la Figura 2.9 es diferente al


presentado en la Figura 2.5. La forma en que un rbol binario se construye depende del
ordenamiento inicial de los elementos en la lista. La lista ordenada resultante,
independientemente del orden inicial, siempre ser la misma. As, la lista ordenada
mostrada en la Figura 2.7 tambin ser la lista ordenada para el rbol binario de la
Figura 2.9.

Figura 2.9: Otro rbol de Bsqueda Binaria

Antes de aprender acerca de otra forma de usar un rbol binario llamado heap, se va a
ampliar la comprensin de rboles binarios a rboles que tienen ms de dos hijos. Tales
rboles se llaman rboles generales.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 181

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

6. Aplicaciones de rboles
Algunas aplicaciones que pueden usar un rbol como una estructura de datos se
presentan a continuacin.

6.1 Representacin e Implementacin de Expresiones Aritmticas

Los rboles pueden representar expresiones aritmticas. Pueden usarse en la


implementacin de expresiones aritmticas y en compiladores. Los rboles se usan
para construir los que se llaman rboles de 'expresin' para evaluar expresiones. Las
expresiones que slo tienen operadores unarios y binarios se pueden representar
usando el rbol binario. Las expresiones de la naturaleza f(a, b, c, d) se
representan tpicamente usando rboles generales.

6.2 Algoritmos de Bsqueda

Una de las principales aplicaciones de los rboles es la bsqueda, esto es, buscar
informacin especifica basada en algn valor clave. Algunos tipos especiales de rboles
ayudan a acelerar el proceso de bsqueda.

6.3 Representacin e Implementacin de Sistemas de Archivos

Los sistemas de archivos son representados e implementados como estructuras de


rboles. El mantenimiento de directorios de archivos y la organizacin jerrquica de
archivos se hacen usando rboles. Los rboles tienen un nmero de aplicaciones en
actividades relacionadas a sistemas de archivos en los sistemas operativos.

6.4 Aplicaciones en Compiladores

Los rboles tienen importantes aplicaciones en compiladores. La fase de anlisis de


sintaxis de los compiladores hace uso del anlisis lexicogrfico (parse trees), donde la
salida es usualmente en la forma de rboles de anlisis lexicogrfico (parse trees). La
parte de anlisis semntico de los compiladores tambin hace uso de tipos especiales
de rboles. Las tcnicas de anlisis lexicogrfico (parse trees) y anlisis semntico
dependen mucho de los rboles. Los utilitarios que ayudan a registrar (trace) las
llamadas de funciones recursivas hacen uso de rboles.

6.5 Procesamiento de Texto

Las aplicaciones de procesamiento de texto hacen uso de rboles como estructuras de


datos. Por ejemplo, un libro puede ser organizado como captulos y secciones, que es
una forma de estructura jerrquica. Varias aplicaciones de procesamiento de texto
requieren que el texto sea organizado en forma de rbol.

6.6 Compresin de Datos

Los algoritmos de compresin de datos hacen uso del rbol de codificacin de Huffman
(una forma especial de rbol). Aqu, el rbol es usado como una estructura de datos que

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 182

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

ayuda en la compresin de los datos de entrada dados. Otro rbol especial, llamado un
rbol sufijo, tambin se usa en las aplicaciones de compresin de datos.

6.7 Aplicaciones Genealgicas

Los rboles son las estructuras de datos naturales a ser usadas en las aplicaciones
genealgicas. Las representaciones de rboles genealgicos y las aplicaciones
basadas en rboles genealgicos, emplean la estructura de datos rboles. Se pueden
tener tales aplicaciones en relaciones jerrquicas para especies vivas, tribus y an
lenguajes.

6.8 rboles de Decisin para Juegos

Varios juegos requieren que las estrategias y reglas estn embebidas. Las decisiones
tienen que hacerse basadas en una estrategia que evale los pros y contras de una
opcin. Una de las estructuras de datos naturales que puede usarse es un rbol de
decisin. Los programas de juegos, especialmente aquellos que involucran estrategias,
tales como, ajedrez o bridge hacen uso de rboles de decisin.

6.9 Representacin de Relaciones Jerrquicas

Los rboles se pueden usar como estructuras de datos en todas las aplicaciones que
involucran la representacin de relaciones jerrquicas y las dependencias entre las
entidades. Ejemplos de estas son los organigramas y relaciones de autoridad de
trabajo.

6.10 Aplicaciones en Bases de Datos

Los rboles tienen numerosas aplicaciones en bases de datos, especialmente con


sistemas de informacin geogrfica, bases de datos espaciales y bases de datos
especiales para mantener catlogos astronmicos.

6.11 Aplicaciones en Ciencias Biolgicas y Bio-informtica

En esta rea, los rboles se han usado como estructuras de datos para agrupar
expresiones genticas, caracterizacin y prediccin de estructuras protenicas, etc. Los
rboles tambin han sido aplicados como parte del proceso de clculo para el diseo de
bases de datos para recursos biolgicos, extraccin de datos, patrones de bsqueda y
descubrimiento, rboles filogenticos y agrupamiento.

Los rboles binarios tambin se usan para representar otra estructura de datos, llamada
heap. A continuacin se discuten brevemente los conceptos relacionados a la estructura
de datos heap.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 183

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

7. Heaps
Un heap se define como un rbol binario que satisface ciertas propiedades especficas.
Los elementos guardados en los nodos deben satisfacer unas cuantas propiedades
especificas, que se listan a continuacin.
Todas las hojas del rbol binario deben ocurrir en dos niveles adyacentes.
Todas las hojas del menor nivel del rbol binario ocurren a la izquierda del rbol.
Todos los niveles del rbol binario estn completos, excepto en el caso del
menor nivel del rbol, que puede estar slo parcialmente completo.
El elemento guardado en la raz es mayor o igual que los elementos guardados
en sus hijos (note que el rbol puede no tener hijos) para el heap mximo.
Los subrboles izquierdo y derecho, que emanan de la raz, son heaps en s
mismos.
Las primeras tres condiciones aseguran que la representacin del rbol binario en
ubicaciones contiguas ser eficiente en trminos de espacio. Esto es conocido como la
propiedad estructural de un heap.

Las dos ltimas condiciones especifican el ordenamiento de los elementos guardados


en el rbol binario o heap. Este ordenamiento se conoce como un heap mximo. Las
dos ltimas condiciones que especifican el ordenamiento pueden ser invertidas, y
cuando esto ocurre, el elemento en la raz es menor o igual que los elementos en sus
hijos. Esto es llamado un heap mnimo. Las dos ltimas condiciones que especifican el
ordenamiento de los elementos son conocidas como la propiedad de orden de un heap.

La Figura 2.11 muestra un rbol binario y el heap asociado. Muestra un heap mnimo.
Se ha usado ordenamiento de nivel para mostrar la lista de elementos. La raz se lista
primero (nivel 0), seguida por los elementos a la izquierda de la raz y luego a la
derecha de la raz (nivel 1). Siguiendo esto, se listan los elementos en el nivel 2 de
izquierda a derecha y as sucesivamente.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 184

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Figura 2.11: Un rbol Binario y Un Heap

Un heap de ejemplo, con valores en los nodos que satisfacen las propiedades de heap,
se muestra en la Figura 2.12. Es un heap mnimo, dado que el valor en el nodo raz es
menor o igual que el valor de los elementos en sus hijos.

Figura 2.12: Un Heap Mnimo


La Figura 2.13 muestra un heap mximo, donde el elemento en el nodo raz es mayor o
igual que el valor de los elementos en sus hijos. Para el mismo conjunto de elementos

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 185

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

mostrado en la Figura 2.12 como heap mnimo, la Figura 2.13 muestra un heap mximo.
La creacin de un heap depende de la lista inicial de elementos.

Figura 2.13: Un Heap Mximo

8. Aplicacin de Heaps
El rea de aplicacin ms importante y til de un heap es la implementacin de una cola
de prioridades, que a su vez, tiene aplicacin en diferentes reas.

8.1 Cola de Prioridad

Un heap se usa en la implementacin de una cola de prioridad. Una cola se llama cola
de prioridad cuando la eliminacin est basada ya sea en un elemento mnimo o
mximo en la cola.

Una cola de prioridad tiene varias aplicaciones, desde aquellas en sistemas operativos
para aplicaciones de encolamiento general. Las colas de prioridad se pueden usar en
planificadores de sistemas operativos donde las tareas esperando por el CPU son
ordenadas de acuerdo a una prioridad. El almacenamiento de eventos dependientes del
tiempo emplea colas de prioridad. Las colas de prioridad se usan ampliamente en
aplicaciones de simulacin de sistemas. En la simulacin digital de eventos discretos,
existe la necesidad de mantener colas de prioridad desde las cuales las entidades sern
seleccionadas para el servicio.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 186

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que Ud. ha completado esta unidad, debe ser capaz de:
Definir un rbol como una estructura de datos.
Discutir rboles binarios, rboles de bsqueda binaria y rboles generales.
Explicar los tres mtodos de recorrido para un rbol binario.
Definir un heap.
Distinguir entre un heap mnimo y un heap mximo.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 187

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 2: Examen de Autoevaluacin


1) Un nodo en un rbol slo puede ser de un tipo simple como un entero.
a) Verdadero.
b) Falso.

2) Cul de estos es un rbol nulo?


a) Un rbol en el que no existen nodos.
b) Un rbol que no existe.
c) Un rbol con todos sus nodos con su parte de informacin nula.
d) Ninguno de los anteriores.

3) El (La) ______ de un rbol es el nmero mximo de nodos desde la raz hasta la


menor hoja en el rbol.
a) Arista.
b) Longitud.
c) Nivel.
d) Altura.

4) Dados dos nodos A y B, el segmento de lnea mostrado entre A y B se conoce


como _____.
a) Profundidad.
b) Longitud.
c) Camino.
d) Arista.

5) Cmo se llama el orden del recorrido, izquierdo, derecho, raz?


a) Preorden.
b) Inorden.
c) Postorden.

6) Cul de los siguientes usa el rbol binario como ordenamiento de jerarqua


fundamental?
a) Heap mnimo.
b) rbol de bsqueda binaria.
c) Heap mximo.
d) Ninguno de los anteriores.

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 188

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

7) Cul de los siguientes recorridos da el orden de los elementos a partir de un rbol


de bsqueda binaria?
a) Inorden.
b) Preorden.
c) Postorden.
d) Ninguno de los anteriores.

8) Para representar una funcin de la clase myFunction(var1, var2, var3,


var4, var5), Cul de las siguientes estructuras de datos ser la eleccin
apropiada?
a) Heaps.
b) rboles binarios.
c) rboles de bsqueda binaria.
d) rboles Generales.

9) En un heap, todas las hojas pueden estar en cualquiera de los niveles.


a) Verdadero.
b) Falso.

10) Qu propiedad de heap establece que el elemento en la raz es al menos tan


grande como los elementos en sus hijos?
a) Propiedad de Estructura.
b) Propiedad de Ordenamiento.

Libro 1: Estructura de Datos y Algoritmos Unidad 2: rboles 189

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Respuestas a la Unidad 2: Examen de Autoevaluacin


1) b
2) a
3) d
4) d
5) c
6) a, b y c
7) a
8) d
9) b
10) b

Unidad 2: rboles Libro 1: Estructura de Datos y Algoritmos 190

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 3: Tcnicas Simples de


Ordenamiento
Objetivos del Aprendizaje
Al final de esta unidad, Usted debe ser capaz de:
Proporcionar una visin general de las tcnicas de ordenamiento.
Explicar el algoritmo de ordenamiento por insercin.
Explicar el algoritmo de ordenamiento por burbuja.
Explicar el algoritmo de ordenamiento por seleccin.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 191

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

1. Introduccin
En las unidades anteriores, se abarc principalmente el tema de estructuras de datos,
sus operaciones e implementaciones. Ahora se sabe que ordenar y buscar elementos
son dos de las actividades ms comunes en cualquier aplicacin grande. En esta
unidad, se tratarn estos dos importantes temas y se presentarn algunos algoritmos de
ordenamiento.

Las aplicaciones que manejan grandes cantidades de datos requieren de algn tipo de
ordenamiento. Se pueden tomar varios ejemplos de tales aplicaciones en la vida real,
tales como:
Ordenar libros y diarios en una biblioteca, por orden de autor, ao de publicacin
y ttulo.
Ordenamiento alfabtico de nombres en un directorio telefnico.
Listar palabras en un diccionario.
Ordenar resultados de motores de bsqueda, basados en su relevancia para el
tema buscado.
Las tcnicas de ordenamiento son principalmente de dos categoras:
Ordenamiento Interno: Se aplica cuando los elementos a ser ordenados estn
disponibles en la memoria primaria.
Ordenamiento Externo: Se aplica cuando los elementos a ser ordenados son
muchos y estn disponibles slo en dispositivos de almacenamiento secundario.
En esta unidad, se tratarn slo las tcnicas de ordenamiento interno. Se aprendern
primero tres tcnicas simples de ordenamiento.

2. Tcnicas Simples de Ordenamiento


Las tres tcnicas de ordenamiento a estudiar son:
Ordenamiento por Insercin.
Ordenamiento de Burbuja.
Ordenamiento por Seleccin.
2.1 Ordenamiento por Insercin

Asuma que se tiene que ordenar un arreglo de enteros llamado InArray. Los elementos
de este InArray, deben ser ordenados en orden ascendente y guardados en otro
arreglo llamado OutArray. El arreglo de entrada InArray tiene que permanecer sin
cambios durante el proceso de ordenamiento. Inicialmente, no hay elementos en
OutArray, dado que los elementos sern guardados en l, slo despus que hayan
sido ordenados.

Se empieza seleccionando cada elemento de InArray, desde el inicio hasta el final, e


insertando cada elemento en un lugar apropiado en OutArray. Esto se hace, de tal

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 192

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

forma que en cualquier etapa, OutArray estar ordenado. El proceso se completa


despus de que todos los elementos de InArray se hayan considerado e insertado en
OutArray.

Las vistas de OutArray durante el ordenamiento por insercin se muestran en la Figura


3.1. Existen seis elementos a ser ordenados en este ejemplo.

Figura 3.1: Vistas de la Insercin desde InArray hacia OutArray

En cada etapa del ordenamiento por insercin, OutArray est ordenado. Cada
elemento de InArray se toma e inserta en su posicin correcta en OutArray. Cuando
se hace la insercin en OutArray, el elemento a ser insertado se compara con cada
elemento en OutArray. Cuando el elemento a ser insertado es menor que el elemento
actual en OutArray, la comparacin se detiene. Desde el elemento donde se detuvo
la comparacin hasta el ltimo elemento en Outarray, los elementos son desplazados
una posicin. El elemento desde InArray es insertado en el agujero que fue creado al
desplazar los otros elementos. Esta tcnica se conoce como ordenamiento por
insercin, dado que se crea un agujero y luego se inserta el elemento.

Se va a entender cmo se llega a cada etapa.


El primer elemento a ser insertado en OutArray es 260. Dado que este es el
primer elemento se coloca en la posicin 0.
El segundo elemento a ser insertado es15 que es menor que 260. El elemento
260 se desplaza una posicin y 15 es insertado en su lugar.
El tercer elemento 20, es mayor que 15 y menor que 260. Cuando se compara
20 con 15, 20 es mayor. Por ello, se contina comparando con el elemento en
la siguiente posicin, 260. Dado que 20 es menor que 260, 260 se desplaza
una posicin y 20 es insertado en su lugar.
El cuarto elemento 30, es mayor que los primeros dos elementos en OutArray
y menor que 260. Nuevamente, 260 se desplaza una posicin para acomodar
30 en su lugar.
El quinto elemento 11 es mayor que 15, pero menor que 20. Los elementos
20, 30 y 260 son desplazados una posicin, y en el lugar de 20, se inserta 11.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 193

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

La ltima etapa involucra colocar 19 en su posicin correcta. Como 19 es


menor que el primer elemento en OutArray, todos los elementos en OutArray
son desplazados una posicin, y 19 es insertado en la posicin 0.
Para ilustrar los pasos involucrados, la transicin desde (e) a (f) se muestra en la Figura
3.2.

Figura 3.2: Transicin desde (e) a (f) en la Figura 3.1

Se usaron dos arreglos, InArray y OutArray, slo para clarificar la ilustracin del
mtodo. Se puede realizar el ordenamiento por insercin en el mismo arreglo.

2.1.1. Programa para el Ordenamiento por Insercin


Al explicar el ordenamiento por insercin usando la Figura 3.1, se han usado dos
arreglos, y as la insercin fue bastante directa. A continuacin se presenta el programa
que realiza un ordenamiento por insercin. Dado que se usa un slo arreglo en el
cdigo C que se da a continuacin, es necesario el uso de una variable temporal para
guardar el elemento ith en cada iteracin. La funcin toma el nmero de elementos en el
arreglo como n y ordena los elementos desde la posicin 0 hasta la posicin n-1. Esto
quedar claro cuando se vea el ejemplo luego del cdigo.

El cdigo C inicia aqu


1. typedef int Tipo_elemento;
2. void insertionSort(Tipo_elemento *inArray,
Tipo_elemento n) {
3. /* Variable para guardar un valor temporalmente */
4. Tipo_elemento tempHolder; //variable manteniendo
temporal
5.
6. /* Declaracin de contadores del ciclo */
7. Tipo_elemento i, j;
8. /* Ciclo Externo: Recorrer el arreglo desde 1 a n - 1
*/
9. for (i = 1; i < n; i++) {

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 194

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

10. /* Guardar el elemento i-simo temporalmente */


11. tempHolder = inArray[i];
12. /* Ciclo Interno: Elementos a ser desplazados
hasta
13. encontrar la posicin del arreglo donde podemos
insertar */
14. j = i - 1;
15. while(j >= 0 && tempHolder < inArray[j]) {
16. inArray[j + 1] = inArray[j];
17. j--;
18. }
19. /* En este punto se puede insertar el valor
guardado en */
20. /* tempHolder en la posicion (j+1)simo del
arreglo */
21.
22. inArray[j + 1] = tempHolder;
23. }
24. /* Ahora tenemos el arreglo ordenado */
25. }
El cdigo C termina aqu

La ejecucin a travs del cdigo C se muestra en la Figura 3.3 con los valores de i, j,
tempHolder, mostrados en cada etapa. Tambin se muestra el orden de elementos en
el arreglo antes y despus del ordenamiento. La secuencia de ejecucin de sentencias
para cada i esta encerrado en un cuadro. Los elementos en el arreglo son los mismos
que los elementos iniciales en la Figura 3.1.
Antes de ordenar: 260 -15 20 30 11 -19

i = 1 tempHolder = -15
Valores actuales en el arreglo: 260 -15 20 30 11 -19
j = 0, tempHolder es menor que inArray[0], inArray[1] = inArray[0]
Despus de ciclo interno: j = -1, inArray[0] = tempHolder
Valores en el arreglo ahora son: -15 260 20 30 11 -19

i = 2 tempHolder = 20
Valores actuales en el arreglo: -15 260 20 30 11 -19
j = 1, tempHolder es menor que inArray[1], inArray[2] = inArray[1]

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 195

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Despus de ciclo interno: j = 0, inArray[1] = tempHolder


Valores en el arreglo ahora son: -15 20 260 30 11 -19

i = 3 tempHolder = 30
Valores actuales en el arreglo: -15 20 260 30 11 -19
j = 2, tempHolder es menor que inArray[2], inArray[3] = inArray[2]
Despus de ciclo interno: j = 1, inArray[2] = tempHolder
Valores en el arreglo ahora son: -15 20 30 260 11 -19

i = 4 tempHolder = 11
Valores actuales en el arreglo: -15 20 30 260 11 -19
j = 3, tempHolder es menor que inArray[3], inArray[4] = inArray[3]
j = 2, tempHolder es menor que inArray[2], inArray[3] = inArray[2]
j = 1, tempHolder es menor que inArray[1], inArray[2] = inArray[1]
Despus de ciclo interno: j = 0, inArray[1] = tempHolder
Valores en el arreglo ahora son: -15 11 20 30 260 -19

i = 5 tempHolder = -19
Valores actuales en el arreglo: -15 11 20 30 260 -19
j = 4, tempHolder es menor que inArray[4], inArray[5] = inArray[4]
j = 3, tempHolder es menor que inArray[3], inArray[4] = inArray[3]
j = 2, tempHolder es menor que inArray[2], inArray[3] = inArray[2]
j = 1, tempHolder es menor que inArray[1], inArray[2] = inArray[1]
j = 0, tempHolder es menor que inArray[0], inArray[1] = inArray[0]
Despus de ciclo interno: j = -1, inArray[0] = tempHolder
Valores en el arreglo ahora son: -19 -15 11 20 30 260

Despus de ordenamiento: -19 -15 11 20 30 260

Figura 3.3: Ejecucin del Programa de Ordenamiento por Insercin

A continuacin se discute el algoritmo de ordenamiento por burbuja.

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 196

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

2.2 Ordenamiento por Burbuja (Bubble Sort)

El algoritmo de ordenamiento por burbuja es uno de los ms simples y ms usado para


ordenar. Este algoritmo tampoco requiere de un segundo arreglo para ordenar los
elementos de un arreglo, pero usa el arreglo original, InArray, para ordenar. El
algoritmo se describe a continuacin.
Paso 1: Ingresar arreglo InArray.

Paso 2: Empezar con el inicio del arreglo InArray con k = 0.

Paso 3: Comparar dos elementos consecutivos de InArray, llamados, InArray


[k] y InArray [k+1].
Paso 4: Si (InArray [k] > InArray [k+1]), intercambiar (InArray [k], InArray [k+1]).
Paso 5: Avanzar al siguiente elemento de InArray con k++. Si k < N-1,
entonces ir al paso 3, caso contrario ir al paso 6.
Paso 6: Se ha completado una pasada a travs del arreglo. Si ocurri al menos
un intercambio de elementos, volver al paso 2, caso contrario ir al paso 7.
Paso 7: Fin del algoritmo.
En la tcnica de ordenamiento por burbuja, slo ocurre una pasada cuando ocurre un
intercambio de elementos. Si no ocurren intercambios, esto implica que el arreglo ya
est ordenado.

Nota: Para determinar si los elementos en el arreglo estn ordenados o no, el arreglo
es recorrido al menos una vez.
Por lo tanto, la ventaja de este algoritmo es que, si el arreglo de entrada est ordenado,
el arreglo se verifica slo una vez. Las vistas de cada pasada se muestran en la Figura
3.4.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 197

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Figura 3.4: Vistas del Ordenamiento por Burbuja

El nombre de ordenamiento por burbuja se le da a este algoritmo dado que el mayor


elemento burbujea a su ubicacin correcta en el arreglo (s es ascendente), despus

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 198

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

de cada pasada. En la Figura 3.4, 260 burbujea a su lugar despus de la primera


pasada, 30 burbujea a su lugar en la segunda pasada, y as sucesivamente. Cuando se
convierte el algoritmo en un programa C, se debe asegurar que no se compara el
elemento ya 'burbujeado' en la siguiente iteracin.

2.2.1. Programa para el Ordenamiento por Burbuja


El programa que realiza el ordenamiento usando el algoritmo de ordenamiento por
burbuja se da a continuacin. Para ingresar al ciclo externo inicialmente se establece la
variable interchange a 1. Posteriormente, el valor que la variable toma dentro del
while determina si el arreglo est ordenado o no. Al entrar en el ciclo while, se
establece interchange a 0. Durante la ejecucin del ciclo for si ocurre al menos un
cambio, entonces interchange se retorna a 1. Si no ocurren intercambios,
interchange permanece en 0 y el algoritmo no entrar al ciclo while externo al
terminar el ciclo for.

El cdigo C inicia aqu


1. typedef int Tipo_elemento;
2. void bubbleSort(Tipo_elemento *inArray, Tipo_elemento
n) {
3. Tipo_elemento i, temp, interchange, j;
4.
5. interchange = 1;
6. j = 1;
7. while(interchange) {
8. interchange = 0;
9. for(i=0;i < n-j; i++) {
10. if(inArray[i] > inArray[i+1]) {
11. // Intercambia los elementos
12. temp = inArray[i];
13. inArray[i] = inArray[i+1];
14. inArray[i+1] = temp;
15. interchange = 1;
16. }
17. }
18. j++;
19. }
20. }
El cdigo C termina aqu

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 199

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

En el algoritmo de ordenamiento por burbuja, la variable j se usa para asegurar que el


elemento intercambiado no sea comparado en la siguiente iteracin. El ciclo for se
ejecuta desde 0 hasta n j. La ejecucin a travs del programa de ordenamiento por
burbuja se da en la Figura 3.5.
Antes de ordenar: 260 -15 20 30 11 -19

Pasada # 1, valor de interchange = 0


Valores actuales en el arreglo: 260 -15 20 30 11 -19
i = 0, inArray[0] > inArray[1]
Intercambio realizado, valor de interchange ahora = 1
i = 1, inArray[1] > inArray[2]
Intercambio realizado, valor de interchange ahora = 1
i = 2, inArray[2] > inArray[3]
Intercambio realizado, valor de interchange ahora = 1
i = 3, inArray[3] > inArray[4]
Intercambio realizado, valor de interchange ahora = 1
i = 4, inArray[4] > inArray[5]
Intercambio realizado, valor de interchange ahora = 1
Valores en el arreglo ahora son: -15 20 30 11 -19 260

Pasada # 2, valor de interchange = 0


Valores actuales en el arreglo: -15 20 30 11 -19 260
i = 0, inArray[0] > inArray[1]
No se realizo intercambio
i = 1, inArray[1] > inArray[2]
No se realizo intercambio
i = 2, inArray[2] > inArray[3]
Intercambio realizado, valor de interchange ahora = 1
i = 3, inArray[3] > inArray[4]
Intercambio realizado, valor de interchange ahora = 1
Valores en el arreglo ahora son: -15 20 11 -19 30 260

Pasada # 3, valor de interchange = 0

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 200

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Valores actuales en el arreglo: -15 20 11 -19 30 260


i = 0, inArray[0] > inArray[1]
No se realizo intercambio
i = 1, inArray[1] > inArray[2]
Intercambio realizado, valor de interchange ahora = 1
i = 2, inArray[2] > inArray[3]
Intercambio realizado, valor de interchange ahora = 1
Valores en el arreglo ahora son: -15 11 -19 20 30 260

Pasada # 4, valor de interchange = 0


Valores actuales en el arreglo: -15 11 -19 20 30 260
i = 0, inArray[0] > inArray[1]
No se realizo intercambio
i = 1, inArray[1] > inArray[2]
Intercambio realizado, valor de interchange ahora = 1
Valores en el arreglo ahora son: -15 -19 11 20 30 260

Pasada # 5, valor de interchange = 0


Valores actuales en el arreglo: -15 -19 11 20 30 260
i = 0, inArray[0] > inArray[1]
Intercambio realizado, valor de interchange ahora = 1
Valores en el arreglo ahora son: -19 -15 11 20 30 260

Pasada # 6, valor de interchange = 0


Valores actuales en el arreglo: -19 -15 11 20 30 260
No se realizo intercambio
Valores en el arreglo ahora son: -19 -15 11 20 30 260

Despus de ordenar: -19 -15 11 20 30 260

Figura 3.5: Ejecucin a travs de Programa de Ordenamiento por Burbuja

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 201

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

En la ltima pasada, (la sexta pasada, en este caso), no se entra al ciclo for, dado que
n j debe ser 6 6 = 0. Como interchange permanece en 0, tambin termina
el ciclo while.

A continuacin se aprender acerca del ordenamiento por seleccin.

2.3 Ordenamiento por Seleccin

Se va a aplicar la tcnica de ordenamiento por seleccin para ordenar un arreglo


InArray que contiene n elementos. Primero, se selecciona el elemento ms pequeo
en el arreglo y se coloca en la primera posicin (en la posicin InArray[0])
intercambiando posiciones con el elemento en InArray[0]. El elemento ms
pequeo puede encontrarse en cualquier posicin, pos, en InArray. Por lo tanto,
InArray[0] se inserta en InArray[pos]. Luego, se busca el siguiente elemento
ms pequeo en InArray, a partir de la posicin 1 en adelante. Cuando se encuentra,
se asigna nuevamente a pos y se intercambia InArray[1] con InArray[pos]. Esto
se repite durante n-1 pasadas, es decir, hasta que alcanza el final del arreglo. El
arreglo est ordenado despus de completar todas las pasadas.

Dicho en palabras simples, el ordenamiento por seleccin involucra encontrar el


elemento mnimo y realizar un intercambio. La Figura 3.6 ilustra el ordenamiento por
seleccin.

Figura 3.6: Vistas del Ordenamiento por Seleccin

La tcnica obtiene el nombre de ordenamiento por seleccin, dado que el elemento ms


pequeo en el arreglo es seleccionado y colocado en la ubicacin correcta. En la Figura
3.6, ocurre un intercambio consigo mismo en la posicin (b) y (e). Se entender porqu
y cmo ocurre este intercambio consigo mismo, cuando se escriba el programa para el
ordenamiento por seleccin.

2.3.1. Programa para Ordenamiento por Seleccin


A continuacin se presenta un programa que permite el ordenamiento de un arreglo por
la tcnica de ordenamiento por seleccin.

El cdigo C inicia aqu


1. typedef int Tipo_elemento;

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 202

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

2. void selectionSort(Tipo_elemento *inArray,


Tipo_elemento n) {
3. Tipo_elemento i, pos, j, min, temp;
4.
5. for(i = 0; i <= n - 2;i++) {
6. // Encontrar el ms pequeo desde i hasta n-1
7. min = inArray[i];
8. pos = i;
9. for (j = i + 1; j <= n - 1; j++)
10. if (inArray[j] < min) {
11. min = inArray[j];
12. pos = j;
13. }
14. // Mnimo encontrado en pos, intercambiar
15. temp = inArray[i];
16. inArray[i] = inArray[pos];
17. inArray[pos] = temp;
18. }
19. }
El cdigo C termina aqu

La ejecucin a travs del programa se ilustra en la Figura 3.7. En cada etapa, un


elemento mnimo es encontrado e intercambiado con el elemento en inArray[i].
Antes de ordenar: 260 -15 20 30 11 -19

i = 0
Valores actuales en el arreglo: 260 -15 20 30 11 -19
Elemento mnimo inicial es 260
j = 1
inArray[1] es menor que el elemento mnimo 260
Nuevo elemento mnimo es -15
j = 2
inArray[2] es mayor o igual que el elemento mnimo -15
j = 3
inArray[3] es mayor o igual que el elemento mnimo -15
j = 4
inArray[4] es mayor o igual que el elemento mnimo -15

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 203

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

j = 5
inArray[5] es menor que el elemento mnimo -15
Nuevo elemento mnimo es -19
Elemento mnimo en arreglo luego de fin de ciclo interno: -19
Intercambiando elemento mnimo -19 con 260 en inArray[0]
Valores ahora en arreglo: -19 -15 20 30 11 260

i = 1
Valores actuales en el arreglo: -19 -15 20 30 11 260
Elemento mnimo inicial es -15
j = 2
inArray[2] es mayor o igual que el elemento mnimo -15
j = 3
inArray[3] es mayor o igual que el elemento mnimo -15
j = 4
inArray[4] es mayor o igual que el elemento mnimo -15
j = 5
inArray[5] es mayor o igual que el elemento mnimo -15
Elemento mnimo en arreglo luego de fin de ciclo interno: -15
Intercambiando elemento mnimo -15 con -15 en inArray[1]
Valores ahora en arreglo: -19 -15 20 30 11 260

i = 2
Valores actuales en el arreglo: -19 -15 20 30 11 260
Elemento mnimo inicial es 20
j = 3
inArray[3] es mayor o igual que el elemento mnimo 20
j = 4
inArray[4] es menor que el elemento mnimo 20
Nuevo elemento mnimo es 11
j = 5
inArray[5] es mayor o igual que el elemento mnimo 11

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 204

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Elemento mnimo en arreglo luego de fin de ciclo interno: 11


Intercambiando elemento mnimo 11 con 20 en inArray[2]
Valores ahora en arreglo: -19 -15 11 30 20 260
i = 3
Valores actuales en el arreglo: -19 -15 11 30 20 260
Elemento mnimo inicial es 30
j = 4
inArray[4] es menor que el elemento mnimo 30
Nuevo elemento mnimo es 20
j = 5
inArray[5] es mayor o igual que el elemento mnimo 20
Elemento mnimo en arreglo luego de fin de ciclo interno: 20
Intercambiando elemento mnimo 20 con 30 en inArray[3]
Valores ahora en arreglo: -19 -15 11 20 30 260

i = 4
Valores actuales en el arreglo: -19 -15 11 20 30 260
Elemento mnimo inicial es 30
j = 5
inArray[5] es mayor o igual que el elemento mnimo 30
Elemento mnimo en arreglo luego de fin de ciclo interno: 30
Intercambiando elemento mnimo 30 con 30 en inArray[4]
Valores ahora en arreglo: -19 -15 11 20 30 260

Despus de ordenar: -19 -15 11 20 30 260

Figura 3.7: Ejecucin a travs de Programa de Ordenamiento por Seleccin

De la Figura 3.7, se observa que ocurre un intercambio innecesario cuando el elemento


mnimo ya est en su ubicacin correcta en el arreglo. Por ejemplo, el elemento -15 fue
intercambiado consigo mismo y de igual forma el elemento 30. Para evitar estos
intercambios redundantes, se puede establecer una marca antes de ingresar al ciclo
interno. Se establece la marca a false. Si el min cambia dentro del ciclo, se establece
la marca a true. Despus de salir del ciclo, se verifica la marca. Si la marca tiene un
valor true, entonces se hace el intercambio, en caso contrario, no se necesita realizar
ningn intercambio.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 205

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Se ha aprendido acerca de tres tcnicas simples de ordenamiento en esta unidad. En


la Unidad 5: Tcnicas Avanzadas de Ordenamiento, se discuten otras dos tcnicas, el
ordenamiento merge-sort (ordenamiento de fusin) y el ordenamiento quicksort
(ordenamiento rpido).

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 206

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que Ud. ha completado esta unidad, debe ser capaz de:
Proporcionar una visin general de las tcnicas de ordenamiento.
Explicar el algoritmo de ordenamiento por insercin.
Explicar el algoritmo de ordenamiento por burbuja.
Explicar el algoritmo de ordenamiento por seleccin.

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 207

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Unidad 3: Examen de Autoevaluacin


1) Cul de los siguientes mtodos de ordenamiento es el ordenamiento por
seleccin?
a) Ordenamiento interno.
b) Ordenamiento externo.

2) Cul de las siguientes tcnicas de ordenamiento coloca el mayor valor en la lista


en su lugar correcto en el arreglo, mientras ordena los elementos en orden
ascendente?
a) Ordenamiento por insercin.
b) Ordenamiento por seleccin.
c) Ordenamiento por burbuja.

3) Cul de las siguientes tcnicas de ordenamiento guarda el valor inicial en una


variable temporal y luego lo asigna a su ubicacin correcta en el arreglo?
a) Ordenamiento por insercin.
b) Ordenamiento por seleccin.
c) Ordenamiento por burbuja.

4) Cul de las siguientes es una condicin de verificacin de correccin para el


algoritmo de ordenamiento por burbuja, asumiendo que es un ordenamiento
descendente?
a) if (inArray[i+1] < inArray[i])
b) if (inArray[i] > myArrayinArray[i+1])
c) if (inArray[i] < inArray[i+1])
d) Ninguna de las anteriores.

5) Cul de los siguientes algoritmos de ordenamiento encuentra el elemento mximo


en la primera pasada mientras ordena en forma descendente?
a) Ordenamiento por seleccin.
b) Ordenamiento por burbuja.
c) Ordenamiento por insercin.

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 208

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

6) Si los siguientes son los resultados intermedios, con la primera fila indicando el
arreglo de entrada, y la ltima fila indicando el arreglo ordenado. Qu algoritmo
de ordenamiento ha sido usado?
-1 0 100 -4 -34 300 210 101
-1 0 100 -4 -34 300 210 101
-1 0 100 -4 -34 300 210 101
-4 -1 0 100 -34 300 210 101
-34 -4 -1 0 100 300 210 101
-34 -4 -1 0 100 300 210 101
-34 -4 -1 0 100 210 300 101
-34 -4 -1 0 100 101 210 300
a) Ordenamiento por burbuja.
b) Ordenamiento por seleccin.
c) Ordenamiento por insercin.

7) En la tcnica de ordenamiento por insercin, cuando n es 10, el contador de ciclo


i se mueve desde 1 hasta 10.
a) Verdadero.
b) Falso.

8) Si el arreglo ya est ordenado, el nmero de pasos que el algoritmo de


ordenamiento por burbuja puede hacer es:
a) 2
b) n
c) 0
d) 1

9) En el ordenamiento de seleccin, cuando n es 12, el ciclo externo se mueve desde


__________________
a) 0 a 11
b) 1 a 12
c) 0 a 10
d) 1 a 10

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 209

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

10) En el ordenamiento de seleccin, cuando n es 12 e i es 4, el ciclo interno se


mueve desde
a) 5 a 11
b) 5 a 10
c) 4 a 11
d) 4 a 10

Unidad 3: Tcnicas Simples de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 210

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Respuestas a la Unidad 3: Examen de Autoevaluacin


1) a
2) c
3) a
4) c
5) a
6) c
7) b
8) d
9) c
10) a

Libro 1: Estructura de Datos y Algoritmos Unidad 3: Tcnicas Simples de Ordenamiento 211

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 4: Laboratorio de Tcnicas


Simples de Ordenamiento
Objetivos del Aprendizaje
Al final de esta unidad, Ud. debe ser capaz de:
Escribir algoritmos de ordenamiento simples y eficientes.
Distinguir entre los diferentes algoritmos de ordenamiento.
Modificar un algoritmo de ordenamiento genrico para ajustarlo a una situacin
particular.

Libro 1: Estructura de Datos y Algoritmos


Unidad 4: Laboratorio de Tcnicas Simples de Ordenamiento 213

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Ejercicio de Laboratorio
Considere un arreglo que almacena enteros. Escriba un programa completo en C que
realice las siguientes tareas:
1) Leer de entrada n un entero positivo mayor que cero. Luego toma como entrada
n elementos enteros, nuevamente elementos enteros positivos mayores que
cero y los ingresa en el arreglo.
2) Ordenar el arreglo de tal forma que todos los nmeros impares ocurran antes
que los nmeros pares.
3) Ordenar todos los nmeros impares en orden descendente.
4) Ordenar todos los nmeros pares en orden ascendente.
Tener en cuenta los siguientes puntos en el programa:
Si no hay enteros pares en la entrada, realizar slo ordenamiento descendente.
Si no hay enteros impares en la entrada, realizar slo ordenamiento ascendente.
Si hay tanto enteros pares como impares en la entrada, realizar las tres
operaciones de ordenamiento.
Para cada tarea de ordenamiento, use una tcnica de ordenamiento diferente.

Consejos tiles
Escriba el programa modular.
Escriba tres funciones:
- ascendSort para ordenar los elementos en orden ascendente. Use el
algoritmo de ordenamiento por insercin.
- descendSort para ordenar los elementos en orden descendente. Use el
algoritmo de ordenamiento por seleccin.
- oddEvenSort para colocar todos los nmeros impares ante de los nmeros
pares en el arreglo. Use el algoritmo de ordenamiento por burbuja.
Ingrese el nmero de elementos a ser guardados en el arreglo. Asegrese que
es un entero positivo mayor que cero.
Ingrese los valores para el arreglo. Realice la validacin de entrada para
asegurarse que slo valores positivos mayores que cero se tomen como
entrada. Dado que el nmero de elementos a ser ingresados al arreglo es
conocido de la primera entrada de datos, ese valor se puede usar para iterar y
obtener los elementos para el arreglo.
Primero, realizar el ordenamiento descendente.
Luego, seguir con el ordenamiento impar-par. Al final de este ordenamiento,
todos los nmeros impares deben estar ordenados en forma descendente,
adems todos los nmeros impares deben ocurrir antes de los nmeros pares
en el arreglo.

Unidad 4: Laboratorio de Tcnicas Simples de Ordenamiento


Libro 1: Estructura de Datos y Algoritmos 214

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Finalmente, ordene slo los nmeros pares en el arreglo en orden ascendente.


Para hacer esto, pase las ubicaciones de inicio y fin de los nmeros pares en el
arreglo. Escriba la funcin de ordenamiento ascendente con tres argumentos,
llamados, el arreglo a ser ordenado, as como las ubicaciones de inicio y fin de
los nmeros pares en el arreglo.
Haga las verificaciones apropiadas para llamar a las tres funciones, basndose
en el tipo de la entrada de enteros.

Libro 1: Estructura de Datos y Algoritmos


Unidad 4: Laboratorio de Tcnicas Simples de Ordenamiento 215

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 5: Tcnicas Avanzadas de


Ordenamiento
Objetivos del Aprendizaje
Al final de esta unidad, Usted debe ser capaz de:
Explicar la tcnica de merge sort (ordenamiento por fusin).
Describir cmo escribir un algoritmo para desarrollar la tcnica de ordenamiento
por fusin.
Explicar la tcnica de quicksort (ordenamiento rpido).
Describir cmo escribir un algoritmo para desarrollar la tcnica de ordenamiento
rpido.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 217

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

1. Introduccin
En la Unidad 3: Tcnicas de Ordenamiento Simple, se aprendieron tres tcnicas de
ordenamiento: por insercin, por burbuja y por seleccin. En esta unidad, se discuten
dos tcnicas de ordenamiento muy usadas, el ordenamiento merge sort (por fusin) y el
ordenamiento quick sort (rpido).

El mtodo de dividir un problema en porciones manejables es llamado dividir y


conquistar. Aplicando este concepto al ordenamiento, los pasos generales involucrados
en un mtodo de dividir y conquistar para ordenamiento son los siguientes:
Ingresar el arreglo.
Dividir el arreglo de entrada en dos arreglos, arreglo X y arreglo Y.
Ordenar el arreglo X por separado.
Ordenar el arreglo Y por separado.
Fusionar los arreglos ordenados X e Y en un solo arreglo.
Este arreglo nico fusionado estar ordenado. Dos preguntas surgen en este punto.
Estas son:
Qu mtodo se debe seguir para dividir la lista en dos?
Qu mtodo se debe seguir para fusionar las listas separadas?
Estas preguntas pueden responderse con la ayuda de dos mtodos que se usan
popularmente como tcnicas de ordenamiento dividir y conquistar, el ordenamiento por
fusin y el ordenamiento rpido.

2. Ordenamiento Merge Sort (por Fusin o Mezcla)


En este mtodo la lista original se puede dividir en dos arreglos de casi el mismo
tamao. Los dos arreglos se ordenan por separado. Los dos subarreglos ordenados son
luego fusionados en un slo arreglo ordenado, de ah el nombre de ordenamiento por
fusin. En esta unidad, se usar una pequea variacin de este mtodo. En vez de
dividir explcitamente el arreglo en dos, se trabaja con grupos de elementos separados
en el arreglo, que pueden ser considerados como equivalentes a dividir el arreglo en
dos subarreglos.

La Figura 5.1 ilustra como funciona el ordenamiento merge sort (por fusin).

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 218

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Figura 5.1: Ordenamiento por Fusin

Est claro a partir de la Figura 5.1 que cada divisin reduce el arreglo a la mitad.
Empezando con el arreglo original consistente de 1*1 = 1 arreglo, se divide el arreglo
en 1*2 = 2 arreglos. De estos dos arreglos, se obtiene 2*2 = 4 arreglos y finalmente
de estos cuatro arreglos se obtienen 4*2 = 8 arreglos. Existen ocho elementos en el
arreglo y as observe que existen (n/2)*2 = n arreglos al final, cuando n = 8. En
esta etapa, slo existe un elemento en cada uno de los n arreglos, que est ordenado.

Luego se fusionan cada par de arreglos, ordenando los elementos en el arreglo


mientras se fusionan. Finalmente, se llega a un slo arreglo conteniendo los elementos
ordenados. A partir de ocho arreglos se obtiene 8/2 = 4 arreglos ordenados, que
llevan a 4/2 = 2 arreglos ordenados. Estos dos arreglos finalmente son fusionados y
ordenados, as se obtiene un arreglo final ordenado.

Note que en cada subarreglo se aplica nuevamente el ordenamiento merge sort (por
fusin) para llegar a la siguiente lista ordenada y fusionada.

Del ejemplo mostrado en la Figura 5.1, se puede ver que el algoritmo de ordenamiento
merge sort (por fusin) tiene algunas propiedades especiales. Estas son:
Despus del primer paso por el arreglo, los arreglos de un slo elemento son
fusionados en arreglos con dos elementos cada uno. Dentro de cada subarreglo
los elementos estn ordenados. En otras palabras, si el arreglo slo tiene dos
elementos a ordenar, slo tomar una pasada.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 219

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Despus del segundo paso por el arreglo, los arreglos de dos elementos son
fusionados en arreglos con cuatro elementos cada uno, esto es, 22 elementos
cada uno, y dentro de cada arreglo los elementos estn ordenados. En otras
palabras, si el arreglo slo tiene cuatro elementos a ordenar, requerir dos
pasadas.
Despus del tercer paso por el arreglo, los arreglos de cuatro elementos son
fusionados en arreglos con ocho elementos cada uno, esto es, 23 elementos
cada uno y dentro de cada subarreglo los elementos estn ordenados. En otras
palabras, si el arreglo tiene slo ocho elementos para ordenar, requerir tres
pasadas.
Despus del paso p por el arreglo, los arreglos de p/2-elementos sern
fusionados en arreglos conteniendo 2p elementos y dentro de cada subarreglo
los elementos estn ordenados. En otras palabras, si el arreglo tiene slo 2p
elementos a ordenar, tomar p pasadas. Suponga que se escribe:
2p = x
A partir de la definicin de logaritmos, se puede escribir
p = log2 x
Por lo tanto, para ordenar n elementos en un arreglo, requerir de log2 n
pasadas.
Basados en esta discusin, se puede escribir un programa para realizar el
ordenamiento por fusin usando las siguientes funciones:
MergeSort: Esta funcin toma como entrada el arreglo a ser ordenado y el
nmero de elementos en el arreglo y controla el ordenamiento merge sort (por
fusin) invocando a las funciones apropiadas. Estas funciones ayudan a crear
particiones de tamaos apropiados durante cada pasada. Tambin ayudan a
calcular el lmite superior de los subarreglos, a ordenar subarreglos, fusionarlos
y asignarlos al arreglo auxiliar.
CalculateUpperBound: Calcula el lmite superior del subarreglo que se crea.
SortAndAssign: Esta funcin ordena los subarreglos individuales y los asigna al
arreglo auxiliar, dummy.
assignSub
assignRemaining
Estas dos ltimas funciones realizan esencialmente la misma tarea, esto es,
asignar los subarreglos ordenados al arreglo auxiliar, dummy. La primera funcin
hace la asignacin de los subarreglos apropiadamente divididos mediante el
procedimiento de ordenamiento por fusin. La segunda funcin trabaja con la
parte restante del subarreglo.
Un programa completo en C que ordena un arreglo de entrada usando el ordenamiento
merge sort (por fusin) se presenta a continuacin. El algoritmo de ordenamiento merge
sort (por fusin) puede ser escrito como un algoritmo tanto iterativo como recursivo. Se
presenta la solucin iterativa.

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 220

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

En la funcin presentada a continuacin, no se realiza una divisin fsica de los


arreglos. Como se sabe, la ltima divisin resulta en n arreglos, cada uno conteniendo
slo un elemento. Se comienza asumiendo que el algoritmo est en este punto. Se
empieza fusionando los n arreglos de un solo elemento directamente.

El cdigo C inicia aqu


1. # define MAX_SIZE 100
2. int calculateUpperBound(int lowerBound2, int size, \
3. int listSize) {
4. if((lowerBound2 + size 1) < listSize)
5. return lowerBound2 + size - 1;
6. else
7. return listSize -1;
8. }
9.
10. void sortAndAssign(int lb1, int lb2, int ub1, int ub2,
11. int *i, int *j, int *k, int x[], int dummy[]) {
12. for(*i = lb1, *j = lb2; *i <= ub1 && *j <= ub2; *k =
*k+1){
13. if(x[*i] <= x[*j]) {
14. dummy[*k] = x[*i];
15. *i = *i + 1;
16. }
17. else {
18. dummy[*k] = x[*j];
19. *j = *j + 1;
20. }
21. }
22. }
23.
24. void assignSub(int i, int ub, int *k, int x[], int
dummy[]) {
25. int numLoop = 0;
26.
27. while (i <= ub) {
28. dummy[*k] = x[i++];
29. *k = *k + 1;
30. }

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 221

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

31. }
32.
33. void assignRemaining(int lb1, int k, int n, int x[],int
dummy[]) {
34. int i;
35. for(i = lb1; k < n; i++) {
36. dummy[k++] = x[i];
37. }
38. }
39. void mergeSort(int *myArray, int n) {
40. int dummy[MAX_SIZE], i=0, j=0, targetIndex=0;
41. int loopCount = 0, lowerBound1, lowerBound2;
42. int upperBound1, upperBound2,size;
43.
44. size = 1;
45. while(size < n) {
46. lowerBound1 = 0;
47. targetIndex = 0;
48. while(lowerBound1 + size < n) {
49. lowerBound2 = lowerBound1 + size;
50. upperBound1 = lowerBound2 - 1;
51. upperBound2 = \
52.
calculateUpperBound(lowerBound2,size, n);
53. sortAndAssign(lowerBound1, \
54.
lowerBound2,upperBound1, \
55. upperBound2, &i, &j,
&targetIndex, \
56. myArray, dummy);
57. assignSub(i, upperBound1, &targetIndex, \
58. myArray, dummy);
59. assignSub(j, upperBound2, &targetIndex, \
60. myArray, dummy);
61. lowerBound1 = upperBound2 + 1;
62. }
63. assignRemaining(lowerBound1, targetIndex, n, \
64. myArray, dummy);

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 222

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

65. for(i = 0; i < n; i++)


66. myArray[i] = dummy[i];
67. size *= 2;
68. }
69. }
El cdigo C termina aqu

Las dos funciones que llaman mergeSort, sortAndAssign y assignSub, usan el


mecanismo de pasar-por-referencia, dado que los cambios en las variables en estas
funciones deben ser visibles en la funcin que las llama. La ejecucin a travs del
algoritmo se observa en la Figura 5.2.
Antes de ordenar: 106 101 204 210 203 201 240 168
Pasada 1:
Ordenar y fusionar: (101 106)
Ordenar y fusionar: (204 210)
Ordenar y fusionar: (201 203)
Ordenar y fusionar: (168 240)

Pasada 2:
Ordenar y fusionar: (101 106 204 210)
Ordenar y fusionar: (168 201 203 240)

Pasada 3:
Ordenar y fusionar: (101 106 168 201 203 204 210 240)
Despus de ordenar: 101 106 168 201 203 204 210 240

Figura 5.2: Ejecucin del Ordenamiento por Fusin

Relacionando la Figura 5.2 con la Figura 5.1, se observa que las pasadas 1, 2, y 3 de la
Figura 5.1 corresponden con las pasadas 1, 2, y 3 de la Figura 5.2.

3. Ordenamiento Quicksort (Rpido)


El algoritmo de ordenamiento quicksort (rpido) est basado en principios similares al
algoritmo de ordenamiento merge sort (por fusin).

Sin embargo, la divisin se hace con mayor sofisticacin e implicacin. Un paso


importante es seleccionar un elemento clave, llamado un pivote. Los elementos se
colocan de tal forma que los elementos con valores menores, que el elemento pivote,
estn a la izquierda del arreglo, mientras que los elementos mayores, que el elemento

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 223

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

pivote, estn a la derecha del arreglo. El arreglo se divide as en dos usando el


elemento pivote. Estos dos subarreglos se ordenan por separado y se fusionan, de
manera que el arreglo combinado resultante est ordenado.

El algoritmo de ordenamiento quicksort (rpido), que fue desarrollado originalmente por


C. A. R. Hoare, est basado en los mismos principios que el algoritmo de ordenamiento
merge sort (por fusin). Slo la forma en que el arreglo es dividido en subarreglos difiere
del algoritmo de ordenamiento merge sort (por fusin).

La Figura 5.3, ilustra un ejemplo del algoritmo quicksort.

Figura 5.3: Ordenamiento (Quicksort)

Como se puede observar en la Figura 5.3, se eligi un elemento aleatorio en la lista


como elemento pivote. En cada etapa, el elemento elegido como elemento pivote se
muestra con un par de corchetes alrededor. A partir de la lista original se eligi 210
como el elemento pivote. El arreglo es dividido en la ubicacin del elemento pivote en el
arreglo. Los subarreglos en la primera pasada contienen:
106 101 204 210 201 203 240 y 168

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 224

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Los subarreglos ahora son divididos nuevamente usando la misma regla. Esto es, el
algoritmo se aplica nuevamente en los subarreglos en forma individual. Despus de
cada pasada, el elemento pivote elegido se mueve a su ubicacin correcta en el arreglo.
En la tercera fila 204 est en su ubicacin correcta dado que fue elegido como el
elemento pivote en la segunda pasada. Al final, se encuentra que el arreglo ha sido
ordenado dado que cada elemento pivote se ha movido a su ubicacin correcta durante
una pasada.

La eleccin del elemento pivote puede ser en forma aleatoria entre los elementos del
arreglo. Un mtodo bueno, aceptable es considerar tres elementos en el arreglo - el
elemento ms a la izquierda, el elemento ms a la derecha y el elemento en el punto
medio del arreglo. Con estos elementos, se puede elegir el elemento medio para que
acte como elemento pivote. Como ejemplo, considere la siguiente lista de elementos:
106 101 204 210 201 203 240 168
Para encontrar la mediana de la lista, se va a encontrar primero el punto medio usando
la frmula:
(posicin_ms_izquierda + posicin_ms_derecha)/2
Usando esto, se obtiene (0 + 7)/2 = 3. Se empieza en cero dado que C empieza
sus ndices de arreglo con cero. El elemento en la posicin_ms_izquierda es
106, el elemento en la posicin_ms_derecha es 168 y el elemento medio es 210.
La mediana de (106, 168, 210) es 168. 168 debe ser elegido como el elemento pivote y
los subarreglos deben ser divididos alrededor del elemento pivote 168.

An otro mtodo de encontrar el elemento pivote es simplemente tomar el elemento en


el punto medio en el arreglo. Se emplea este mtodo simple de encontrar un elemento
pivote al escribir la funcin para quicksort en C. Se va a escribir una solucin recursiva
para quicksort. Se han escrito cuatro funciones para hacer el ordenamiento usando
quicksort. Cada uno de estos se lista y discute brevemente a continuacin.

A partir de la funcin main se hace una llamada a la funcin quickSort con el arreglo
a ser ordenado y el nmero de elementos como parmetros.

El cdigo C inicia aqu


/* Programa Quicksort */
/* Esta funcin slo lanza el proceso de quicksort,
invocando la funcin Do_Quick_Sort */
void quickSort (int *myArray, int n) {
doQuickSort(myArray, 0, n-1,n);
}
El cdigo C termina aqu

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 225

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

La funcin quickSort simplemente hace una llamada a la funcin recursiva


doQuickSort con tres argumentos, el arreglo a ser ordenado, el punto de inicio y la
ubicacin final del arreglo. La funcin doQuickSort se da a continuacin.

El cdigo C inicia aqu


1. // Algoritmo quicksort recursivo
2. void doQuickSort(int *myArray, int left_pos, \
3. int right_pos, int len_array) {
4. int pivotElementIndex, k, i;
5.
6. if (left_pos < right_pos) {
7. pivotElementIndex = arrangeArray(myArray, \
8. left_pos, right_pos, len_array);
9.
10. printf("izquierda: %d, derecha: %d
",left_pos,right_pos);
11. printf("\nIndice del elemento pivote:
%d\n",pivotElementIndex);
12. printf("-----------------------------------------
-----------\n");
13. printf("\n");
14. doQuickSort(myArray, left_pos, pivotElementIndex-
1, len_array);
15. doQuickSort(myArray, pivotElementIndex+1, right_pos,
len_array);
16. }
17.
18. }
El cdigo C termina aqu

La funcin doQuickSort verifica si left_pos es menor que right_pos. Si es as, el


ndice del elemento pivote es recibido. Usando este ndice se divide el arreglo en forma
lgica invocando nuevamente a doQuickSort en forma recursiva.

La funcin arrangeArray encuentra el elemento pivote y lo mueve a su ubicacin


correcta en el arreglo. Retorna el ndice del elemento pivote en el arreglo despus de
moverlos.

El cdigo C inicia aqu


1. int arrangeArray(int *myArray, int left_pos, \

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 226

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

2. int right_pos, int len_array) {


3. int i, k, pivotElement, temp;
4.
5. // Obtiene el elemento pivote
6. pivotElement = findPivotElement(myArray, \
7. left_pos, right_pos, len_array);
8.
9. // Guarda la ubicacin de la posicin ms a la
izquierda
10. // en una variable temporal
11. k = left_pos;
12. // Usando el elemento pivote y su ubicacin encuentra
la
13. // ubicacin correcta para el elemento pivote en
el arreglo
14. i = left_pos;
15. while(i <= right_pos) {
16. if (pivotElement > myArray[i]) {
17. k++;
18. if (k != i) {
19. temp = myArray[k];
20. myArray[k] = myArray[i];
21. myArray[i] = temp;
22. printf("temp: %d, k: %d, i: %d\n", temp,
k, i);
23. }
24. printArray(myArray, len_array, k,
left_pos, right_pos);
25. printf("\n");
26. }
27. i++;
28. }
29. temp = myArray[left_pos];
30. myArray[left_pos] = myArray[k];
31. myArray[k] = temp;
32. printf("\n temp: %d, k: %d, i: %d\n", temp, k, i);
33. printArray(myArray, len_array, k, left_pos,
right_pos);

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 227

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

34. printf("\n--------------- El Arreglo Ordenado ---------


-----------\n");
35. printArray(myArray, len_array, k, left_pos,
right_pos);
36. return k;
37. }
El cdigo C termina aqu

Se ha escrito una funcin separada para encontrar el elemento pivote. Si se quiere


cambiar el mtodo de eleccin del elemento pivote, entonces todo lo que se debe hacer
es modificar esta funcin. Antes de retornar, esta funcin coloca el elemento pivote en
la posicin ms izquierda del arreglo, que es usada por la funcin arrangeArray para
mover los elementos a su ubicacin correcta.

El cdigo C inicia aqu


1. int findPivotElement(int *myArray, int left_pos, \
2. int right_pos, int len_array) {
3. int mid_point, temp;
4. int k;
5. mid_point = (left_pos + right_pos)/2;
6. printf("\n----------- El Arreglo con Nuevo Pivote -
-----------\n");
7. printArray(myArray, len_array, mid_point, left_pos,
right_pos);
8. printf("----------------------------------------------
------\n");
9.
10. // Cambia el elemento ms a la izquierda con el
elemento del Punto
11. // medio. Retorna el elemento ms a la izquierda como
el elemento
12. // pivote a la funcin que lo llama
13. temp = myArray[left_pos];
14. myArray[left_pos] = myArray[mid_point];
15. myArray[mid_point] = temp;
16.
17. return (myArray[left_pos]);
18. }
El cdigo C termina aqu

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 228

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

A continuacin se muestra el cdigo de las funciones printArray y main que


permiten visualizar la ejecucin del mtodo Quicksort.

El cdigo C inicia aqu


1. void printArray(int *myArray, int n, int pivotIndex,
int leftIndex, int rightIndex) {
2. int i;
3. for (i=0; i<n; i++) {
4. if (i==leftIndex){
5. printf("(");
6. }
7. if (i==pivotIndex)
8. printf(" [%d] ", myArray[i]);
9. else
10. printf(" %d ", myArray[i]);
11. if (i==rightIndex){
12. printf(")");
13. }
14. }
15. printf("\n");
16. }
/* Programa Quicksort */
/* Esta funcin slo lanza el proceso de quicksort,
invocando la funcin Do_Quick_Sort */
void quickSort (int *myArray, int n) {
doQuickSort(myArray, 0, n-1,n);
}
17.
18. int main ()
19. {
20. int arr[] = {106, 101, 204, 210, 203, 201, 240,
168};
21. quickSort(arr, 8);
22. system("pause");
23. }
El cdigo C termina aqu

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 229

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

La ejecucin a travs del quicksort se presenta en la Figura 5.4. Se ha mostrado cada


llamada recursiva hecha con un nmero. En cada etapa, se encuentra que el orden de
los elementos en el arreglo, despus del ordenamiento, est basado en el elemento
pivote. Se nota que el elemento pivote mueve su ubicacin correcta en el arreglo en
cada llamada recursiva.

Antes de ordenar: 106 101 204 210 201 203 240 168

Llamada Recursiva # 1

Elemento Pivote = 210


Llamando PRIMERO a doQuickSort con 0 y 7

------------- El Arreglo con Nuevo Pivote --------------


( 106 101 204 [210] 201 203 240 168 )
---------------------------------------------------------
( 210 [101] 204 106 201 203 240 168 )

( 210 101 [204] 106 201 203 240 168 )

( 210 101 204 [106] 201 203 240 168 )

( 210 101 204 106 [201] 203 240 168 )

( 210 101 204 106 201 [203] 240 168 )

temp: 240, k: 6, i: 7
( 210 101 204 106 201 203 [168] 240 )

temp: 210, k: 6, i: 8
( 168 101 204 106 201 203 [210] 240 )

--------------- El Arreglo Ordenado ---------------------


( 168 101 204 106 201 203 [210] 240 )
left: 0, right: 7
ndice del elemento pivote: 6
---------------------------------------------------------

Elementos despus de ordenar: 168 101 204 106 201 203


210 240

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 230

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Llamada Recursiva # 2

Elemento Pivote = 204


Llamando PRIMERO a doQuickSort con 0 y 5

------------- El Arreglo con Nuevo Pivote --------------


( 168 101 [204] 106 201 203 ) 210 240
---------------------------------------------------------
( 204 [101] 168 106 201 203 ) 210 240

( 204 101 [168] 106 201 203 ) 210 240

( 204 101 168 [106] 201 203 ) 210 240

( 204 101 168 106 [201] 203 ) 210 240

( 204 101 168 106 201 [203] ) 210 240

temp: 204, k: 5, i: 6
( 203 101 168 106 201 [204] ) 210 240

--------------- El Arreglo Ordenado ---------------------


( 203 101 168 106 201 [204] ) 210 240
left: 0, right: 5
Indice del elemento pivote: 5
----------------------------------------------------
Elementos despus de ordenar: 203 101 168 106 201 204 210 240

Llamada Recursiva # 3

Elemento Pivote = 168


Llamando PRIMERO a doQuickSort con 0 y 4

------------- El Arreglo con Nuevo Pivote --------------


( 203 101 [168] 106 201 ) 204 210 240
---------------------------------------------------------
( 168 [101] 203 106 201 ) 204 210 240

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 231

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

temp: 203, k: 2, i: 3
( 168 101 [106] 203 201 ) 204 210 240

temp: 168, k: 2, i: 5
( 106 101 [168] 203 201 ) 204 210 240

--------------- El Arreglo Ordenado ---------------------


( 106 101 [168] 203 201 ) 204 210 240
left: 0, right: 4
Indice del elemento pivote: 2
----------------------------------------------------
Elementos despus de ordenar: 106 101 168 203 201 204 210 240

Llamada Recursiva # 4

Elemento Pivote = 106


Llamando PRIMERO a doQuickSort con 0 y 1

------------- El Arreglo con Nuevo Pivote --------------


( [106] 101 ) 168 203 201 204 210 240
---------------------------------------------------------
( 106 [101] ) 168 203 201 204 210 240

temp: 106, k: 1, i: 2
( 101 [106] ) 168 203 201 204 210 240

--------------- El Arreglo Ordenado ---------------------


( 101 [106] ) 168 203 201 204 210 240
left: 0, right: 1
Indice del elemento pivote: 1
----------------------------------------------------
Elementos despus de ordenar: 101 106 168 203 201 204 210 240

Llamada Recursiva # 5

Valor pos izquierdo es mayor que valor pos derecho, retorna


de llamada recursiva.
Elemento Pivote = 203
Llamando SEGUNDO a doQuickSort con 3 y 4

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 232

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

------------- El Arreglo con Nuevo Pivote --------------


101 106 168 ( [203] 201 ) 204 210 240
---------------------------------------------------------
101 106 168 ( 203 [201] ) 204 210 240

temp: 203, k: 4, i: 5
101 106 168 ( 201 [203] ) 204 210 240

--------------- El Arreglo Ordenado ---------------------


101 106 168 ( 201 [203] ) 204 210 240
left: 3, right: 4
Indice del elemento pivote: 4
------------------------------------------------------
Elementos despus de ordenar: 101 106 168 201 203 204 210 240

Figura 5.4: Ejecucin a travs de Quicksort

Para las siguientes pasadas de este ejemplo, se debe ejecutar la funcin recursiva:
doQuickSort(myArray, pivotElementIndex+1, right_pos, len_array);
A pesar de que la lista suministrada ha sido ordenada (para este ejemplo en particular).
Lista despus de ordenar: 101 106 168 201 203 204 210 240

En todos los mtodos de ordenamiento que se aprendieron en esta unidad, los arreglos
fueron ordenados en orden ascendente. Para ordenar en orden descendente, slo se
debe cambiar la condicin de verificacin que decide si es un ordenamiento ascendente
o descendente. Por ejemplo, en el ordenamiento por insercin, se debe cambiar la
condicin en el ciclo while como sigue:
while(j >= 0 && tempHolder > myArray[j]) {
myArray[j + 1] = myArray[j];
j--;
}
Para el ordenamiento ascendente, se usa la siguiente condicin:
tempHolder < myArray[j])

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 233

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

En el ordenamiento por burbuja, ser:


for (i=0;i < n-1; ++i) {
if (myArray[i] < myArray[i+1]) {
temp = myArray[i];
myArray[i] = myArray[i+1];
myArray[i+1] = temp;
interchange = 1;
}
}
Para el ordenamiento ascendente, se ha usado la siguiente condicin:
if (myArray[i] > myArray[i+1])
As, se observa que un cambio simple y apropiado en la condicin verifica entre un
ordenamiento y otro.

En todos los ejemplos, se ha usado un arreglo de enteros para mostrar el ordenamiento


de elementos. Estos elementos pueden ser cadenas o cualquier otro tipo de dato
estructurado. Para tipos de datos estructurados, la comparacin ser tpicamente con
uno de los miembros del tipo de dato estructurado. Por ejemplo, si se tiene una
estructura definida para un tipo de dato definido por el usuario, Person, como sigue:
typedef struct {
char name[30];
char idno[10];
int age;
} Person;
Entonces, cualquiera de los miembros del tipo de dato definido por el usuario se puede
usar para ordenar. As, las tcnicas de ordenamiento que se aprendieron pueden
aplicarse a cualquier tipo de dato, con los cambios apropiados requeridos para el tipo de
dato.

4. Temas Opcionales de Estudio


Los siguientes dos temas, llamados Algoritmos, Complejidad y Comparacin de
Algoritmos de Ordenamiento sern presentados en este curso como temas opcionales
de estudio. El material presentado aqu es avanzado y no es esencial para entender los
algoritmos de ordenamiento cubiertos en este volumen.

5. Algoritmos y Complejidad
Cuando se debe resolver un problema, pueden usarse cierto nmero de algoritmos
diferentes. Raramente se encuentra un problema especfico para el cul solo existe un

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 234

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

algoritmo disponible. Se va a considerar el problema de calcular el factorial de un entero


positivo n dado. Dos algoritmos pueden usarse para resolver este problema. Uno es un
algoritmo iterativo y el otro es un algoritmo recursivo.

El algoritmo iterativo para calcular el factorial de un entero positivo n se puede escribir


como sigue:
factorial = 1;
for (i = 1; i <= n; i++)
factorial = factorial * i;
El algoritmo recursivo para calcular el factorial de un entero positivo n dado se puede
escribir como sigue:
if (n == 0)
return (1);
else
return(n * factorial(n-1));
Cuando un problema puede resolverse usando uno de varios algoritmos disponibles,
cmo se decide que algoritmo es mejor?
En el caso del problema de factorial dado, el ejemplo iterativo puede ser eficiente
computacionalmente, por lo que puede parecer la eleccin apropiada. Sin embargo, la
solucin recursiva es muy simple y clara. Tambin es muy cercana a la definicin
matemtica de factorial. As, esta solucin tiene algunas ventajas tambin.
Algunas de las cualidades deseables de un algoritmo se listan a continuacin:
1) Debe ser simple, claro y fcil de entender.
2) Debe ser fcil de programar en un lenguaje de programacin apropiado y
adems fcil de depurar.
3) Debe hacer uso ptimo de la memoria primaria, esto se conoce como
optimizacin de espacio. En general, un algoritmo que usa menos memoria
primaria es considerado mejor.
4) Debe hacer uso ptimo del CPU, esto se conoce como optimizacin de tiempo.
En general, un algoritmo que se ejecuta ms rpido es considerado mejor.
En la prctica, sin embargo, es difcil obtener todas estas cualidades deseables juntas.
Es posible que un algoritmo que es simple y claro para desarrollar pueda tener un
tiempo de ejecucin relativamente largo. En forma similar, tambin es posible que un
algoritmo que se ejecuta muy rpido no es simple de entender ni fcil de depurar. Sin
embargo, pueden darse algunas guas bsicas. Si el algoritmo a desarrollar necesita
usarse slo una vez, o pocas veces a lo ms, entonces quizs las cualidades deseables
del algoritmo deben ser simplicidad, fcil de entender, fcil de programar y depurar. Por
otro lado, si el algoritmo ser usado casi siempre o si se ejecuta por mucho tiempo, las
cualidades deseables sern tiempo corto de ejecucin y uso ptimo de la memoria
primaria.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 235

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Por otra parte, se ver luego en esta unidad que las estructuras de datos juegan un rol
vital al lograr las cualidades deseables de algoritmos.
A continuacin se explican los factores que afectan el tiempo de ejecucin de un
programa.

5.1 Factores que Afecta el Tiempo de Ejecucin de un Programa

Es til conocer los diferentes factores que afectan el tiempo de ejecucin de los
programas. Algunos de estos factores se listan a continuacin:
La naturaleza y tamao de los datos que se ingresan al programa.
La naturaleza y velocidad de ejecucin de instrucciones en la computadora
usada para ejecutar los programas.
La calidad del cdigo ejecutable generado por el compilador particular del
lenguaje de programacin.
La complejidad de tiempo del algoritmo, basada en la cual fue desarrollado el
programa.
Se explican brevemente cada uno de estos factores.

5.2 Naturaleza y Tamao de los Datos de Entrada


La entrada de datos a un programa afecta el tiempo de ejecucin del programa. El
tamao de la entrada de datos tiene los efectos que pueden observarse ms fcilmente
en el tiempo de ejecucin de los algoritmos.
Por ejemplo, un programa que genera nmeros primos desde 1 a n, donde n es un
nmero entero positivo dado de entrada. Claramente, cuando la entrada de datos es
1000, el algoritmo tomar menos tiempo para ejecutarse que cuando la entrada es
32767. Otro caso, es un algoritmo que ordena un arreglo de enteros en orden
ascendente. El algoritmo tendr un tiempo de ejecucin muy grande cuando los datos
de entrada requieren ordenar un arreglo que contiene 500.000 elementos en
comparacin si el valor de entrada requiere ordenar apenas 1500 elementos.
As, el tamao de los datos de entrada afecta el tiempo de ejecucin de los algoritmos,
especialmente en los algoritmos de bsqueda y ordenamiento. La naturaleza de los
datos de entrada tambin puede afectar el tiempo de ejecucin de los programas.
Por ejemplo, considere un algoritmo que realiza la integracin numrica de una funcin
dada. En este caso, considere que la integracin numrica se hace para la funcin
trigonomtrica seno(x). El tiempo de ejecucin para el algoritmo depender de los dos
puntos dados como entrada, sobre los que se realiza la integracin.
Suponga que el rango de dos entradas representado por los dos puntos es grande,
entonces el algoritmo tender a demorar ms para ejecutarse. Si el rango de las dos
entradas es relativamente pequeo, el algoritmo tender a tomar un tiempo menor para
ejecutarse. La correccin de la salida para la integracin numrica tambin afecta el
tiempo de ejecucin de los programas. Por ejemplo, considere que la salida actual para
un rango de entrada es Y. A travs de la integracin numrica se puede tener la salida

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 236

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

como Y. Suponga que se quiere que |y-y| < 0.01 entonces el tiempo de
ejecucin ser relativamente corto, comparado con un requerimiento de |Y-Y| <
0.000001. Si se acepta un Y, tal que |Y-Y| < 0.01, entonces 0.01 es la
tolerancia de aceptacin. Claramente, una entrada que busca una tolerancia de
aceptacin ms estricta tomar un mayor tiempo de ejecucin del algoritmo, que una
entrada que tiene una tolerancia de aceptacin relativamente baja.

5.3 Naturaleza y Velocidad de Ejecucin de Instrucciones


Uno de los puntos generales a recordar es que, en la mayora de computadoras, las
operaciones de adicin y sustraccin se ejecutan relativamente ms rpido que las
operaciones de multiplicacin y divisin. Por lo tanto, un algoritmo que usa
predominantemente las operaciones de adicin y sustraccin tendr un tiempo de
ejecucin relativamente menor que uno donde predominan las multiplicaciones y
divisiones.
A veces el uso de las operaciones de multiplicacin y divisin (as como del operador
mdulo) es inevitable. En tales casos, si uno de los multiplicandos o divisores es un
nmero que es expresable como una potencia de dos, entonces el algoritmo puede
tener un tiempo de ejecucin que es menor que otros casos. Esto es porque una
operacin de multiplicacin que involucra un multiplicando expresable en trminos de
potencias de dos puede hacer uso del operador de desplazamiento de bits. Por ejemplo,
si se requiere multiplicar un entero k por 16, se puede desplazar el patrn binario para k
a la izquierda 4 bits (24 = 16). En casi todas las computadoras las instrucciones de
desplazamiento de bits se ejecutan ms rpido que la instruccin de multiplicacin. En
forma similar, cuando se necesita dividir k por 16, se puede desplazar el patrn binario
para k a la derecha 4 bits. As el uso de ciertas instrucciones puede disminuir el tiempo
de ejecucin mientras que el uso de otras puede incrementarlo.
Algunas computadoras realizan operaciones para evaluar funciones trigonomtricas
como seno, coseno y tangente, usando un algoritmo de software. Otras
computadoras evalan estas operaciones directamente usando el hardware. Un
algoritmo que usa tales operaciones se puede evaluar ms rpido en una computadora
donde tales instrucciones son ejecutadas en el hardware.
Algunas computadoras son equipadas con mltiples unidades funcionales, tales como
unidades de suma, sustraccin, multiplicacin y divisin. En tales computadoras, los
algoritmos tendrn menor tiempo de ejecucin. Existen tambin computadoras
especializadas tales como procesadores en arreglo y procesadores en vector. Cuando
un algoritmo trata con instrucciones que manejan vectores, puede tener un menor
tiempo de ejecucin en computadoras con capacidad de procesamiento de vectores.
5.4 Calidad del Cdigo Ejecutable Generado por un Compilador
Un algoritmo se escribe como un programa usando un lenguaje de programacin. El
compilador para el lenguaje de programacin genera el cdigo en lenguaje mquina,
que es finalmente ejecutado en la computadora. El tiempo de ejecucin del programa
depende de la calidad del cdigo generado por el compilador.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 237

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Las computadoras con conjuntos de instrucciones complejas (procesadores CISC)


tienen un gran nmero de instrucciones con capacidades extremadamente poderosas.
Casi siempre, los compiladores para lenguajes de programacin no generan cdigo que
pueda tomar ventaja de estas instrucciones disponibles complejas y poderosas, adems
que pueda explotar estas instrucciones. Por otro lado, algunos compiladores realmente
no explotan bien estas instrucciones poderosas. Claramente, un programa compilado
usando un compilador que explota el conjunto de instrucciones de una computadora,
debe contribuir a un menor tiempo de ejecucin que uno que no lo explota.
La calidad del cdigo generado por un compilador afecta el tiempo de ejecucin de los
programas an de otra forma. Algunos compiladores generan cdigo altamente
optimizado, mientras que otros no generan cdigo optimizado.
La optimizacin del cdigo puede lograrse en muchas formas. Por ejemplo, los
operando usados a menudo pueden ser colocados en registros del CPU para uso
futuro. En tales casos los programas tienden a ejecutarse ms rpidos. Las
optimizaciones de cdigo en compiladores tambin pueden hacer optimizaciones de
ciclos (bucles) y muchos otros tipos de optimizaciones. Por lo tanto, un programa
compilado usando un generador de cdigo altamente optimizado puede resultar en un
tiempo de ejecucin menor que un programa compilado sin ninguna optimizacin de
cdigo.

5.5 Complejidad en Tiempo de Algoritmos


La complejidad en tiempo de los algoritmos es el tiempo de ejecucin de un programa
que depende directamente del tamao de los datos de entrada. Se denotar al tamao
de los datos de entrada como n. La complejidad en tiempo de un algoritmo se escribe
como T(n), para indicar que la complejidad en tiempo depende de n.
Considere un arreglo de enteros de n elementos. Se va a asumir que se quiere buscar
la ocurrencia de un elemento especfico en el arreglo empleando el algoritmo de
bsqueda lineal. El algoritmo de bsqueda lineal busca la ocurrencia del elemento en el
arreglo desde la primera posicin a la segunda posicin y as sucesivamente, hasta que
se encuentra el elemento o se alcanza el final del arreglo.
Qu es T(n) en este caso? Esto puede ser confuso, si no se est seguro de cmo
medir el tiempo de ejecucin, y en qu unidades. No se establece explcitamente T(n)
en cuntos milisegundos. En vez de ellos se piensa en l como el nmero de
instrucciones ejecutadas.
En el caso de una bsqueda binaria, se puede pensar en T(n) como el nmero de
comparaciones que se hace para verificar si el elemento existe en una posicin en el
arreglo. Si el elemento que se est buscando ocurre en la primera ubicacin, el nmero
de comparaciones realizadas es uno, si se encuentra en la segunda ubicacin, es dos, y
si se encuentra en la ltima ubicacin o no se encuentra, el nmero de comparaciones
realizadas es n. As que realmente no se puede hablar de un T(n)general. En vez de
ello, se puede hablar de un tiempo de ejecucin del peor caso y un tiempo de ejecucin
del mejor caso. En el caso de una bsqueda lineal, el peor caso ocurre cuando el
elemento se encuentra en la ltima posicin en el arreglo o si no se encuentra en el
arreglo. En este caso, T(n) = n.

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 238

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Tambin se puede hablar de un tiempo de ejecucin 'promedio', o Tavg(n). En el caso


de una bsqueda lineal, se presenta como sigue:
Tavg(n) = 1 + 2 + + n / n
= n(n + 1)/2n
= (n + 1)/2
Cuando n es realmente grande, se puede aproximar (n + 1)/2 por slo n/2. As la
complejidad promedio de tiempo de ejecucin del algoritmo de bsqueda lineal es n/2.
Si el arreglo est en orden ascendente, se puede usar el algoritmo de bsqueda binaria.
En este algoritmo, se elimina la mitad de una zona de bsqueda de una vez. Por lo
tanto, T(n) puede ser mostrado como log2n. As en trminos de tiempo de ejecucin,
una bsqueda binaria es ms eficiente que una bsqueda lineal. Considere un algoritmo
de bsqueda lineal de un arreglo unidimensional de tamao n. El peor caso es cuando
el elemento buscado est en la ltima posicin n o no est presente en el arreglo. Por
ello T(n) = n es la complejidad del peor caso para un algoritmo de bsqueda lineal.

Considere el algoritmo de bsqueda binaria. El peor caso es cuando el elemento


buscado no est presente en el arreglo. En este caso, la bsqueda procede eliminando
repetidamente la mitad de la zona de bsqueda hasta que la zona de bsqueda se
reduce a nada. As en este caso, T(n) = log2n.

Se ha visto el tiempo de ejecucin promedio de los algoritmos de bsqueda lineal y


binaria. En el caso de una bsqueda lineal, el tiempo promedio es (n+1)/2, mientras
que el tiempo de ejecucin del peor caso es n. En el caso de una bsqueda binaria, el
tiempo de ejecucin promedio y el tiempo de ejecucin del peor caso son iguales,
log2n.

Aqu es importante recordar que el tiempo de ejecucin promedio depende de la nocin


de una entrada o conjunto de entradas de datos promedio. En muchos casos, la nocin
de una entrada de datos promedio es difcil de determinar. En algunos casos, el trmino
entrada de datos promedio puede no ser significativo.

5.6 Tasa de Crecimiento de Funciones

Se espera que T(n) se incremente con el incremento en el tamao de entrada n. Ms


que un incremento absoluto, se quiere examinar la tasa de incremento en T(n). Esto
puede hacerse comparando T(n) con algunos de los estndares dados a continuacin:
log2n crecimiento logartmico - crece lentamente
n crecimiento lineal
n log2n crecimiento log-lineal
2
n crecimiento cuadrtico
3
n crecimiento cbico
n
2 crecimiento exponencial crece muy rpido

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 239

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

5.7 Notacin Big-Oh

Una forma de comparar T(n) con estas funciones estndar es usando la notacin
funcional O, llamada la notacin Big-Oh. En vez de proporcionar una definicin
matemtica rigurosa y su explicacin asociada, se proporcionar una explicacin simple
de esta notacin.

Considere el algoritmo de bsqueda lineal. Se sabe que el peor caso de tiempo de


ejecucin es n. Usando la notacin Big-Oh, esto se expresa como se muestra a
continuacin:
T(n) = O(n)
Esto significa simplemente que el tiempo de ejecucin del algoritmo de bsqueda lineal
es proporcional a n, el tamao del arreglo buscado. En otras palabras, la complejidad
del algoritmo de bsqueda lineal crece linealmente.
En forma similar, considere el algoritmo de bsqueda binaria. Se sabe que el tiempo de
ejecucin es log2n. Usando la notacin Big-Oh, esto se expresa como sigue:
T(n) = O(log2 n)
Esto implica que el tiempo de ejecucin de un algoritmo de bsqueda binaria es
proporcional a log2 n. En otras palabras, la complejidad de un algoritmo de bsqueda
binaria crece en forma logartmica. Las tasas de crecimiento logartmico son
consideradas entre las tasas de crecimiento ms lentas. Debido a esto, un algoritmo de
bsqueda binaria es muy eficiente conforme crece el tamao del arreglo.
Ahora asuma que un cierto algoritmo tiene T(n) = 25n3 + 7n2. Usando la notacin
Big-Oh, esto se expresa como:
T(n) = O(n3)
Esto expresa que la complejidad del algoritmo crece cbicamente, con el crecimiento de
la entrada n. As, comparado a otro algoritmo que tiene T(n) = O(n2), que exhibe una
tasa de crecimiento cuadrtico, el algoritmo que exhibe una tasa de crecimiento cbico
es un algoritmo pobre.
La notacin Big-Oh tiene una desventaja. Se pudiera haber escrito T(n) = 25n3 +
7n2 como O(n4) en vez de O(n3). Esto tambin es correcto. Matemticamente,
expresar T(n) = 25n3 + 7n2 como O(n3) es considerado tan aceptable como
O(n4), dado que 25n3 + 7n2 est en un orden cbico, y no un orden cuadrtico. La
desventaja de la notacin Big-Oh referida es la posibilidad de expresar una expresin,
usando ms de un orden de magnitud.

Para completar se dar una definicin matemtica relacionando T(n) y O(n).

T(n) = O(f(n)) si existen dos constantes positivas k y m, tales que


T(n) <= k f(n) para todo n >= m.

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 240

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Cuando se dice que T(n) es O(f(n)) se sabe que f(n) es un lmite superior en la tasa
de crecimiento de T(n). Tambin se puede especificar el lmite inferior en la tasa de
crecimiento de T(n) usando la notacin Big-Omega.
3
T(n) = 25n + 7n es (n ).
3 2

Al analizar algoritmos, el lmite superior en la tasa de crecimiento se consider ms


importante, por lo tanto, la notacin Big-Oh se usa ms a menudo.

5.8 Las Implicaciones de las Tasas de Crecimiento

Para empezar, se asume que los programas se evalan comparando T(n)e ignorando
las constantes de proporcionalidad. As un programa con O(n3) es mejor que uno con
O(2n). El primero tiene un crecimiento cbico mientras que el segundo tiene un
crecimiento exponencial. Tambin es posible que el primer programa tome 50n3
milisegundos para una ejecucin, mientras el segundo toma 3*2n milisegundos.

Se sabe que el crecimiento exponencial es una de las tasas de crecimiento ms


rpidas. Los algoritmos que exhiben esta tasa de crecimiento son pobres. Para valores
de n > 10, puede mostrarse que el tiempo de ejecucin para el segundo programa ser
mayor que el tiempo de ejecucin para el primer programa. Para valores mayores de n,
el segundo programa (con una tasa de crecimiento exponencial) mostrar un
incremento dramtico en el tiempo de ejecucin comparado con el primer programa
(con una tasa de crecimiento cbico). Se puede concluir de esto que son ms
convenientes los programas que tienen un tiempo de ejecucin con menor tasa de
crecimiento.

Existe la tentacin de pensar que no hay que preocuparse por asegurar tasas de
crecimiento menores. Dado que la velocidad de ejecucin de las computadoras se
incrementa, se pueden resolver problemas grandes con igual rapidez debido al
incremento en la velocidad de ejecucin de las computadoras. Sin embargo, esto es
incorrecto.

Cuando los programas exhiben bajas tasas de crecimiento, un incremento en la


velocidad de procesamiento permitir resolver problemas mayores, pero existe un lmite
en el problema ms grande, el cual se puede resolver en una cantidad fija de tiempo.
Los algoritmos con tasas de crecimiento grandes, como tasas de crecimiento cbico o
exponencial, el incremento de la velocidad de procesamiento puede no mostrar ningn
efecto significativo en la posibilidad para resolver problemas grandes. Por lo tanto,
siempre es ventajoso tener una tasa de crecimiento menor, para asegurar el uso ms
eficiente del tiempo.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 241

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

5.9 Cundo es posible pasar por alto los tiempos de ejecucin de


programas?

No siempre es necesario considerar los tiempos de ejecucin de programas como el


nico criterio para evaluar los mismos. Se pueden pasar por alto los tiempos de
ejecucin de programas en ciertos casos. Estos casos se listan a continuacin:
Si un programa va a ser usado una vez o slo pocas veces, el costo de
desarrollo sobrepasa todos los dems factores. Por lo tanto, se elige un
algoritmo que sea fcil de implementar.
Si el mantenimiento de un programa es relevante, la eleccin de un algoritmo
complicado pero eficiente puede no ser apropiado dado que slo el desarrollador
original puede reconocer todas sus implicaciones.
Si un programa va a trabajar slo con tamaos pequeos de datos, la tasa de
crecimiento puede jugar un rol mnimo comparado con el factor constante en el
clculo de tiempo de ejecucin. De tal forma que es posible elegir programas
que tienen grandes tasas de crecimiento pero son 'eficientes' para el propsito.
En algunas aplicaciones, como algoritmos numricos, la eficiencia puede quedar
atrs comparada con la precisin y estabilidad.
Si los algoritmos eficientes requieren mucho espacio de almacenamiento, puede
que no sean las elecciones adecuadas.
Se van a comparar los cinco algoritmos de ordenamiento explicados usando los
conceptos aprendidos acerca de algoritmos, complejidad y notacin O.

6. Comparacin de Algoritmos de Ordenamiento


En esta seccin se comparan los diferentes algoritmos de ordenamiento estudiados en
esta unidad. Se puede hacer la comparacin basada en ciertos atributos, tales como:
La naturaleza del algoritmo, si es iterativo o recursivo.
Si el algoritmo ordena el arreglo en s mismo o usa un arreglo adicional.
La complejidad del algoritmo.
De estos, el atributo ms importante es la complejidad del algoritmo. Un algoritmo
menos complejo se ejecutar usualmente con mayor velocidad, mientras que uno ms
complejo se ejecutar ms lento.

Se puede tener una idea de la complejidad del algoritmo calculando cuntas veces se
ejecuta un ciclo. En todos los algoritmos de ordenamiento, los ciclos iterativos son
establecidos basados en una condicin que involucra una comparacin de dos
elementos del arreglo. Es por esto, que se puede obtener una idea de la complejidad
mirando cuntas veces se hacen comparaciones en el algoritmo. El nmero promedio
de comparaciones realizadas en el algoritmo es una medida indirecta de la complejidad.

Asuma que un algoritmo particular A requiere Na comparaciones, y el algoritmo B


requiere Nb comparaciones. Suponga Na > Nb, entonces se dice que el algoritmo A es

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 242

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

ms complejo que el algoritmo B. Usualmente, en estas condiciones, el algoritmo B se


ejecuta ms rpido que algoritmo A.

A continuacin de presenta la discusin repasando el algoritmo de ordenamiento por


insercin estudiado en la Unidad 3: Tcnicas Simples de Ordenamiento.

6.1 Algoritmo de Ordenamiento por Insercin

El algoritmo de ordenamiento por insercin es un algoritmo iterativo. Permite ordenar un


arreglo en s mismo, sin requerir el uso de un arreglo adicional.

Considere el programa correspondiente al algoritmo de ordenamiento por insercin


dado en la Unidad 3: Tcnicas Simples de Ordenamiento. Especficamente, observe la
siguiente sentencia contenida en el programa:
while(j >= 0 && tempHolder < myArray[j]) {
Esto representa el ciclo ms interno donde se hace una comparacin para controlar el
ciclo. Se debe determinar cuntas veces se ejecuta.
Esto, obviamente, depende de la naturaleza del arreglo de entrada proporcionado.

Considerando el mejor caso de la lista ya ordenada, el ciclo externo se ejecuta n-1


veces. Dado que el arreglo est ordenado, no se ingresa al ciclo interno. As el nmero
de comparaciones es cero y la complejidad es O(n).

Considere el peor caso, cuando el arreglo que es ingresado est ordenado en


exactamente el orden inverso. Considere que se tiene un algoritmo que ordena el
arreglo en orden ascendente, y el arreglo de entrada est en orden descendente. Este
caso sugiere que puede requerir mayor nmero de comparaciones para realizar la tarea
que el requerido en cualquier otro arreglo entrada.

Ahora observe el programa. Cuando el valor de i es 1, el ciclo interno se ejecuta una


vez. Esto es, el nmero de comparaciones realizadas es 1. Cuando i es 2, el ciclo
interno se ejecuta dos veces. En forma similar, cuando i = n-1, el nmero de
comparaciones realizadas es n-1. Por lo tanto, para realizar el ordenamiento, el nmero
total de comparaciones realizadas es:
1 + 2 + 3 +...+ (n-2) + (n-1) = n(n-1)/2
Por lo tanto, la complejidad del ordenamiento por insercin es O(n2) para el peor caso.

6.2 Algoritmo de Ordenamiento de Burbuja (Bubble Sort)

El algoritmo de ordenamiento de burbuja (bubble sort) es un algoritmo iterativo. Permite


el ordenamiento de un arreglo en s mismo, sin el uso de un arreglo adicional.

Considere el programa en la Unidad 3: Tcnicas Simples de Ordenamiento que


implementa el algoritmo de ordenamiento por burbuja. Especficamente, la sentencia
que es la sentencia de comparacin.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 243

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

if(myArray[i] > myArray[i+1])


Considere un caso simple de myArray estando ya en orden ascendente. En este caso,
el ciclo for interno se ejecuta n-1 veces. As se harn n-1 comparaciones.

Como en el algoritmo de ordenamiento por insercin, se va a considerar el mejor y el


peor caso de la lista estando ordenada y en orden inverso.

Para el mejor caso, el ciclo externo se ejecutar slo una vez para asegurar que la lista
est ordenada. El ciclo interno compara cada par. Esto significa que existen n-1
comparaciones. La complejidad en este caso es O(n).

Considerando el peor caso cuando la entrada myArray est en orden descendiente, el


ciclo externo se ejecuta n veces. Para cada ejecucin del ciclo externo, el interno se
ejecuta sucesivamente pocas veces. Esto es porque, al final de cada pasada no se
comparan los elementos, que han sido desplazados a sus posiciones correctas en el
arreglo. As, el nmero de comparaciones requerido es:
(n-1) + (n-2) + (n-3) + + 2 + 1 = n(n 1)/2
Esto es O(n2).

6.3 Algoritmo de Ordenamiento por Seleccin

El algoritmo de ordenamiento por seleccin es un algoritmo iterativo. Permite ordenar un


arreglo en s mismo, sin requerir del uso de un arreglo adicional.

Considere el programa escrito en la Unidad: Tcnicas Simples de Ordenamiento para


implementar el algoritmo de ordenamiento por seleccin. Especficamente, considere la
siguiente sentencia en el ciclo interno del programa:
if (myArray[j] < min)
Lo primero que se observa es que el nmero de comparaciones que se hace no
depende de s el arreglo de entrada ya estaba en orden, o si estaba en orden inverso.
En este algoritmo, se hacen n-1 pasadas a travs del arreglo. En cada pasada se tiene
que encontrar el elemento mnimo. En la primera pasada, se deben hacer (n-1)
comparaciones para encontrar el elemento mnimo. En la segunda pasada, se deben
hacer (n-2) comparaciones para encontrar el elemento mnimo. As, el nmero de
comparaciones que se hace para ordenar el arreglo completo es:
(n-1) + (n-2) + (n-3) +...+ 3 + 2 + 1 = n(n-1)/2
En el ordenamiento por seleccin no existe diferencia entre el mejor y el peor caso,
dado que el nmero de veces que los ciclos externo e interno se ejecutan es el mismo.
No estn basados en alguna condicin especfica. Slo se repiten de 0 a <= n-2 (ciclo
externo) y de i+1 a <= n-1. La complejidad del ordenamiento por seleccin en el
mejor y peor caso es O(n2).

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 244

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

6.4 Ordenamiento Merge Sort (por Fusin)

El algoritmo de ordenamiento merge sort (por fusin) puede ser escrito como un
algoritmo recursivo o como uno iterativo. Se escribi un algoritmo iterativo. Usualmente,
se escribe como un algoritmo recursivo dado que es simple de desarrollar. El algoritmo
de ordenamiento merge sort (por fusin) requiere un arreglo adicional de n elementos.

Ya se ha visto en esta unidad que para que el ordenamiento merge sort (por fusin)
ordene un arreglo completo, requiere de a lo ms log2 n pasadas. Ahora, el programa
que se ha implementado en esta unidad para el algoritmo de ordenamiento merge sort
(por fusin). Especficamente observe la funcin sortAndAssign, que tiene la
sentencia para la comparacin de elementos del arreglo. Durante cada pasada puede
requerir de n comparaciones. As, el nmero total de comparaciones requerir n log2 n,
que es O(n log2 n).

El rendimiento del ordenamiento merge sort (por fusin) es el mismo tanto en el mejor
como el peor de los casos, dado que el arreglo necesita ser dividido, ordenado y
fusionado. Por lo tanto, el ordenamiento merge sort (por fusin) no es tan bueno para el
mejor de los casos como si lo es para el peor caso.

6.5 Ordenamiento Quicksort (Rpido)

El algoritmo de ordenamiento quicksort (rpido) usualmente es un algoritmo recursivo.


Puede desarrollarse en forma iterativa, pero es extremadamente difcil y rara vez
intentado. No usa otro arreglo.

La sentencia requerida para la comparacin ocurre en este caso en la funcin


doQuickSort. Dado que es un algoritmo recursivo, no se obtiene directamente el
nmero de comparaciones.

El peor caso para quicksort ocurre cuando la lista dada ya est ordenada. El algoritmo
tomar n comparaciones slo para obtener que el primer elemento ya est en su
posicin correcta. En este caso, el primer subarreglo contendr slo un elemento. El
segundo subarreglo contiene n-1 elementos. Aqu nuevamente, el segundo subarreglo
requiere de n-1 comparaciones para obtener que el siguiente elemento permanecer
en su posicin correcta. De esta forma el nmero total de comparaciones requerido es:
n + (n-1) + (n-2) + ... + 3 + 2 + 1 = n(n+1)/2
La complejidad del algoritmo es O(n2). El algoritmo quicksort tambin trabaja con dos
subarreglos, como el ordenamiento por fusin.

El mejor caso ocurre cuando el elemento pivote divide la lista dada en exactamente dos
mitades del mismo tamao en cada ocasin. En este caso, se requieren n
comparaciones para colocar el elemento pivote en su ubicacin correcta. El mtodo
quicksort es aplicado en forma recursiva en estos dos subarreglos. Quicksort requiere
de n/2 comparaciones (debido a que en el mejor caso se asume que la lista est
dividida en dos mitades iguales) para cada subarreglo, para colocar los elementos

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 245

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

pivote en sus respectivos subarreglos en su ubicacin correcta. Este proceso es


repetido hasta que existen n/n subarreglos. Por lo tanto, el nmero total de
comparaciones requeridas ser:
n + 2*n/2 + 4*n/4 + log2n =n*log2n
Esto implica que la complejidad del algoritmo quicksort es O(nlog2n).

Note que existen muchas versiones de los algoritmos merge sort (de fusin) y quicksort,
por esto, los nmeros de comparaciones requeridas son aproximados pero tpicos. En
implementaciones particulares, estas figuras pueden ser diferentes.

Una observacin interesante que se puede hacer es que mientras que los
ordenamientos por insercin y burbuja trabajan mejor para una lista ordenada que para
una desordenada, la complejidad algortmica del quicksort para una lista ordenada es
peor que su complejidad para una lista desordenada.

La comparacin de todos estos algoritmos de ordenamiento se resume en la Tabla 3.1.


Algoritmo de Iterativo o Usa Arreglo
Mejor Caso Peor Caso
Ordenamiento Recursivo Adicional

Por Insercin Iterativo No O(n) O(n2)

De Burbuja Iterativo No O(n) O(n2)

Por Seleccin Iterativo No O(n2) O(n2)

Usualmente
Merge Sort recursivo, pero
Si O(n log2 n) O(n log2 n)
(por Fusin) aqu se usa una
versin iterativa
No, pero pueden
Usualmente
Quicksort implementaciones O(n log2 n) O(n2)
recursivo
especficas

Tabla 3.1: Comparacin de Algoritmos de Ordenamiento

A partir de la comparacin de las cinco tcnicas de ordenamiento, el ordenamiento


merge sort (por fusin) tiene menos comparaciones tanto para el mejor como el peor de
los casos. El ordenamiento por seleccin tiene O(n2) tanto para el mejor como el peor
de los casos.

Se mencionaron unos cuantos puntos basados en el estudio emprico realizado de


varias tcnicas de ordenamiento. A pesar que el ordenamiento por insercin tiene el
mismo nmero de comparaciones para el peor caso como el ordenamiento de burbuja,
O(n2), es ms eficiente que el ordenamiento de burbuja. Sin embargo, para listas muy
grandes, el ordenamiento por insercin no es considerado el mejor algoritmo.

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 246

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Los algoritmos ms usados en listas grandes son tanto los algoritmos merge sort (por
fusin) y quicksort (rpido). El ordenamiento quicksort (rpido) se usa en muchas
aplicaciones que usan ordenamientos intensamente, dado que es ms eficiente que el
ordenamiento merge sort (por fusin). El ordenamiento quicksort (rpido) tiene en
general un mejor rendimiento.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 247

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Resumen
Ahora que Ud. ha completado esta unidad, debe ser capaz de:
Explicar acerca de la tcnica de ordenamiento merge sort (por fusin).
Describir cmo escribir un algoritmo para desarrollar la tcnica de ordenamiento
merge sort (por fusin).
Explicar acerca de la tcnica de ordenamiento quicksort (rpido).
Describir cmo escribir un algoritmo para desarrollar la tcnica de ordenamiento
quicksort (rpido).

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 248

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 5: Examen de Autoevaluacin


1) Cul de los siguientes algoritmos de ordenamiento usa el mtodo de dividir y
conquistar para ordenar elementos?
a) Ordenamiento Quicksort (Rpido).
b) Ordenamiento Merge sort (por Fusin).
c) Ambos anteriores.

2) Qu algoritmos de ordenamiento usa otro arreglo durante el ordenamiento?


a) Ordenamiento Quicksort (Rpido).
b) Ordenamiento Merge sort (por Fusin).
c) Ambos anteriores.

3) El ordenamiento merge sort (por fusin) requiere de log2n pasadas para ordenar
un arreglo.
a) Verdadero.
b) Falso.

4) El ordenamiento quicksort (rpido) usa un elemento pivote durante el


ordenamiento.
a) Verdadero.
b) Falso.

5) Cul de los siguientes puede ser usado como elemento pivote?


a) Cualquier elemento aleatorio en el arreglo.
b) La media de tres elementos.
c) El elemento en el punto medio.
d) Todas las anteriores.

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 249

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Preguntas Opcionales
Las preguntas presentadas aqu cubren los temas de Algoritmos, Complejidad y
Comparacin de Algoritmos. Slo debe intentar resolverlas si ha estudiado estos dos
temas.
6) Cul de los siguientes afecta el tiempo de ejecucin de un programa?
a) Tamao de los datos de entrada.
b) Velocidad de ejecucin de las instrucciones.
c) Naturaleza de los datos de entrada.
d) Complejidad en tiempo de los algoritmos.

7) Cul de los siguientes se usa para mostrar un crecimiento logartmico lineal?


a) log2n
b) n log2n
c) Ambas anteriores

8) Si T(n) = 100n3 + 1000n2, es correcto decir que:


T(n) = O(n3)
a) Verdadero.
b) Falso.

9) Cul de las siguientes tcnicas de ordenamiento tiene O(n log2 n) para el peor
de los casos?
a) Ordenamiento por Insercin.
b) Ordenamiento Quicksort (Rpido).
c) Ordenamiento Merge sort (por Fusin).
d) Todos los anteriores.

10) Cul de las siguientes tcnicas de ordenamiento tiene O(n) para el mejor de los
casos?
a) Ordenamiento Merge sort (por Fusin).
b) Ordenamiento por Insercin.
c) Ordenamiento por Burbuja.
d) Ordenamiento por Seleccin.

Unidad 5: Tcnicas Avanzadas de Ordenamiento Libro 1: Estructura de Datos y Algoritmos 250

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Respuestas a la Unidad 5: Examen de Autoevaluacin


1) c
2) b
3) a
4) a
5) d
6) a, b, c y d
7) b
8) a
9) c
10) b y c

Libro 1: Estructura de Datos y Algoritmos Unidad 5: Tcnicas Avanzadas de Ordenamiento 251

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 6: Laboratorio de Tcnicas de


Ordenamiento Avanzadas
Objetivos de Aprendizaje
Al final de esta unidad, usted debe ser capaz de:
Escribir algoritmos de ordenamiento eficientes y simples basados en las tcnicas
aprendidas.
Distinguir entre los diferentes algoritmos de ordenamiento.
Modificar algoritmos de ordenamiento genricos y adaptarlos a una aplicacin
particular.

Libro 1: Estructura de Datos y Algoritmos


Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas 253

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Ejercicio de Laboratorio
Considerar un arreglo que contenga nombres de libros y sus autores. Cada fila en el
arreglo contiene el nombre de un libro, seguido de una coma, un espacio y el nombre
del autor. Un ejemplo de ello se muestra a continuacin:
The Ultimate Guitar Book, Bacon Tony
La sintxis por defecto es:
<nombre de libro>, <nombre de autor>
Se toma la entrada del usuario usando la misma sintaxis. Si no se encuentra ninguna
coma en la entrada, se asume que la entrada es solamente el nombre del libro. Para
simplificar el ejercicio, se asumir que slo se incluye el nombre de un autor, que es el
autor principal del libro.

Ejemplos de entrada se muestran a continuacin:


Data Structures and Program Design in C, Robert L. Kruse
Twelve Red Herrings, Jeffrey Archer
Foundation's Triumph
David Brin
Just For Fun, David Diamond
The Ultimate Guitar Book, Bacon Tony
En el listado anterior, en la tercera y cuarta entrada, no se encuentra la coma. El
programa asumir que estos son los nombres de los libros, a pesar de que la cuarta
entrada se refiere al nombre de un autor. De hecho es el autor de la tercera entrada en
la lista.

Escribir un programa en C que haga lo siguiente:

1) Lea una lista de nombres de libros y sus autores en un arreglo. El final de la fila se
indica con '\n' y el final de la entrada con 'END'.
2) Usando ambas tcnicas de ordenamiento explicadas en la Unidad 5: Tcnicas de
Ordenamiento Avanzado, ordene el arreglo de caracteres y muestre los elementos
ordenados como se muestra:
Data Structures and Program Design in C, Robert L. Kruse
David Brin
Foundation's Triumph
Just For Fun, David Diamond
The Ultimate Guitar Book, Bacon Tony
Twelve Red Herrings, Jeffrey Archer

Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas


Libro 1: Estructura de Datos y Algoritmos 254

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Recomendaciones

1) Crear dos arreglos que contengan los nombres de los libros y de los autores.
3) Leer la informacin dada por el usuario, lnea por lnea, hasta el final de la nueva
lnea. Cada lnea ingresada por el usuario se sobreentiende que contendr el
nombre del libro y el autor.
4) Guardar cada lnea de entrada como una fila en el primer arreglo.
5) Verificar si la palabra 'END' ha sido ingresada. Si es as, finalizar el ingreso y
guardar el nmero de elementos en una variable. En caso contrario, continuar
leyendo la siguiente lnea de entrada del usuario.
6) Al terminar el ingreso de todas las lneas del usuario, copiar el contenido del primer
arreglo hacia el segundo.
7) Mostrar el mensaje Antes de utilizar el ordenamiento quicksort: y
mostrar los elementos del primer arreglo.
8) Ordenar usando quicksort. Recordar realizar los cambios a la funcin de quicksort
para que trabaje con arreglos de caracteres. A continuacin se muestra cmo la
funcin findPivotElement ha sido modificada para manejar arreglos de
caracteres:
char * findPivotElement(Element_type \
elements[ROWSIZE][COLSIZE], int left_pos, \
int right_pos) {
int mid_point;
Element_type temp[COLSIZE];
mid_point = (left_pos + right_pos)/2;
// Intercambiar el elemento ms a la izquierda con l
que
// est a la mitad. Devolver el elemento ms a la
izquierda
// como elemento pivote para la funcin invocada
strcpy(temp, elements[left_pos]);
strcpy(elements[left_pos], elements[mid_point]);
strcpy(elements[mid_point], temp);
return (elements[left_pos]);
}
9) Mostrar el mensaje Despus de utilizar el ordenamiento quicksort:
y mostrar los elementos del arreglo ordenado.
10) Mostrar el mensaje Antes de utilizar ordenamiento merge sort: y
mostrar los elementos del segundo arreglo copiado del primero anteriormente.

Libro 1: Estructura de Datos y Algoritmos


Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas 255

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

11) Ordene usando merge sort. Recordar realizar los cambios a la funcin de merge
sort para que trabaje con arreglos de caracteres. Se muestra a continuacin una
funcin de muestra la cual necesita el cambio:

void assignRemaining(int lb1, int k, int n, \


Element_type elements[ROWSIZE][COLSIZE], \
Element_type dummy[ROWSIZE][COLSIZE]) {
int i;
for(i = lb1; k < n; i++) {
strcpy(dummy[k++], elements[i]);
}
}
12) Mostrar el mensaje Despus de utilizar ordenamiento merge sort: y
mostrar los elementos del arreglo ordenado.

Unidad 6: Laboratorio de Tcnicas de Ordenamiento Avanzadas


Libro 1: Estructura de Datos y Algoritmos 256

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Unidad 7: Tcnicas de Bsqueda


Objetivos de Aprendizaje
Al final de esta unidad, usted debe ser capaz de:
Explicar las diferentes tcnicas de bsqueda.
Diferenciar entre bsqueda interna y externa.
Describir cmo desarrollar un algoritmo para la tcnica de bsqueda lineal.
Describir cmo desarrollar un algoritmo para la tcnica de bsqueda binaria.
Explicar el uso de hashing para insertar y localizar elementos en una tabla hash.
Discutir los mtodos de resolucin de una colisin hash.

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 257

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

1. Introduccin
En esta unidad, se aprender acerca de otra actividad comn en las aplicaciones
conocida como bsqueda. Localizar informacin es una de las operaciones clave en
muchas aplicaciones. Ejemplos abundan en la vida real, como son:
Localizar sinnimos de una palabra en un diccionario.
Localizar la direccin de un alumno de la base de datos universitaria.
Localizar del nmero de cuenta del cliente de un banco.
Localizar todos los agentes de comercio Ferrari en Europa.
Localizar los empleados que han estado trabajando en una organizacin por
ms de 20 aos y estn ganando un salario anual de $1M.
La bsqueda se lleva a cabo basada un elemento particular, el cual es generalmente
una entrada. Este elemento, es la base de la bsqueda, es el llamado elemento de
bsqueda. Tambin se le conoce como elemento clave. El procedimiento usado en
buscar elementos que concuerden con la clave es un aspecto importante de la
bsqueda.

La bsqueda generalmente se divide en dos reas que son:


Bsqueda Interna Cuando todos los registros que se buscan estn en el rea
de memoria primaria.
Bsqueda Externa - Cuando el nmero de registros es demasiado grande y no
se puedan mantener juntos en la memoria primaria. En este caso, la mayor parte
de los registros son guardados en un dispositivo de almacenamiento secundario
y se realiza la bsqueda usando uno de los mtodos de bsqueda externa.
En esta unidad, se discuten solamente la bsqueda interna. Muchos procedimientos
han sido desarrollados para la bsqueda. Se discutirn solo dos de ellos en este curso:
Bsqueda lineal o secuencial.
Bsqueda binaria.

2. Bsqueda Lineal o Secuencial


Considere un arreglo desordenado conteniendo un nmero de elementos. Se desea
hacer la bsqueda de un elemento en este arreglo. Uno de los mtodos ms simples de
bsqueda es comenzar buscando desde la primera posicin del arreglo (ndice es 0),
comprobar la ocurrencia del elemento en esa posicin, y moverse a la siguiente
posicin del arreglo hasta que el elemento es encontrado en una posicin particular o se
llega al final del arreglo y el elemento no es encontrado. El algoritmo se muestra a
continuacin:
Paso 1: Declarar el arreglo que almacenar los elementos.
Paso 2: Leer los elementos hacia el arreglo.
Paso 3: Leer el elemento a buscar.

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 258

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Paso 4: Fijar en un ciclo la variable contadora k a 1.


Paso 5: Si el elemento k en el arreglo es igual al buscado, entonces el elemento es
encontrado. Tomar la accin adecuada. Ir al paso 9.
Paso 6: Si el elemento k no es igual al elemento buscado, entonces incrementar k
en 1.
Paso 7: Si k es mayor que el nmero de elementos en el arreglo, entonces el
elemento no se encuentra. Tomar la accin adecuada. Ir al paso 9.
Paso 8: Ir al paso 5.
Paso 9: Fin del algoritmo.
Ahora, basados en este algoritmo, se escribe el cdigo en C para la bsqueda lineal.

2.1 Programa para la Bsqueda Lineal

El programa toma tres argumentos a saber: el arreglo, el nmero de elementos en el


arreglo y el dato a buscar. La funcin retorna el valor de 0 si el elemento no es
encontrado en el arreglo. De otra manera retorna el valor 1.
int linearSearch(Element_type *elements, int n, \
Element_type element) {
int k, found = 0;

for (k = 0; k < n && !found; k++)


if (elements[k] == element)
found = 1;
return found;
}
Si eI elemento no se encuentra, significa que el arreglo entero es recorrido. El valor de
found permanece en cero. Si el elemento es encontrado, entonces el valor de found
retorna 1. As, al retornar found, se indica el xito o fallo de la bsqueda.

Otra forma de programar la funcin citada es:


int linearSearch(Element_type *elements,int n, \
Element_type element) {
int k;

for (k = 0; k < n; k++)


if (elements[k] == element)
return 1;
return 0;
}
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 259

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

La funcin no utiliza la variable extra found en este caso. El anterior algoritmo es ms


intuitivo, debido a que usa explcitamente la variable found para indicar si el elemento
es encontrado o no. Pero otra forma de escribir la bsqueda lineal es:
int linearSearch(Element_type *elements,int n, \
Element_type element) {
int k;

for (k = 0; k < n && elements[k] != element; k++)


;
if (k < n)
return 1;
else
return 0;
}
En este algoritmo, se usa la condicin elements[k] != element como elemento de
verificacin, entonces k deber ser menor que n en un valor. Si el elemento de
bsqueda no es igual a elements[k], entonces k deber ser igual n. La verificacin
se hace fuera del ciclo, y el valor apropiado se retorna a la funcin que la llam.

El programa main que hace uso de esta funcin se muestra a continuacin:

El cdigo C empieza aqu...


1. The main program
2. #include <stdio.h>
3. typedef int Element_type;
4. int linearSearch(Element_type *, int, Element_type);
int linearSearch(Element_type *elements, int n, \
Element_type element) {
int k, found = 0;

for (k = 0; k < n && !found; k++)


if (elements[k] == element)
found = 1;
return found;
}
5.
6. int main() {
7. Element_type elements[100], element;

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 260

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

8. int k;
9. /* leer n, el nmero de elementos en array */
10. printf("Enter integers elements to fill the array
...\n\n");
11. k = 0;
12. do {
13. printf("Enter an integer ... end with -9999\n");
14. scanf("%d", &element);
15. if (element != -9999)
16. elements[k++] = element;
17. } while (element != -9999);
18.
19. printf("\n\nEnter the integer to search ...\n");
20. scanf("%d", &element);
21. if (linearSearch(elements,k,element))
22. printf("Element %d found in array\n",element);
23. else
24. printf("Element %d not found in
array\n",element);
25. }
El cdigo C termina aqu

3. Bsqueda Binaria
En la Unidad 2 - rboles, se aprendi acerca del rbol de bsqueda binaria y se
present brevemente el concepto de bsqueda binaria. El rbol de bsqueda binaria
sigue el algoritmo binario. A continuacin se va a aprender ms acerca de este
algoritmo.

Este mtodo de bsqueda requiere que el arreglo est ordenado ascendentemente o


descendentemente. En la lista ordenada, el elemento central es comparado con el
elemento a buscar. Si estos coinciden, entonces la bsqueda tuvo xito. Si el elemento
no se encuentra en esta posicin, el algoritmo verifica si el elemento de bsqueda es
mayor o menor que el elemento central. Esto indica si el elemento a buscar ser
encontrado en la parte superior o inferior del arreglo. As, se reduce el nmero de
elementos buscados a la mitad del tamao original. Despus, se aplican los mismos
pasos para buscar el centro del arreglo. Finalmente, si se recorre el arreglo
completamente sin encontrar una coincidencia, la bsqueda no tuvo xito.

Observe el siguiente ejemplo para comprender esto:


Paso 1: Ingresar el arreglo y ordenarlo en forma ascendente.
Paso 2: Ingresar el elemento a buscar.
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 261

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Paso 3: El ndice 0 del arreglo se llamara top, y el ndice n-1 se llamara bot.
Paso 4: Encontrar el elemento central. Para realizar esto se debe encontrar el punto
medio en el arreglo. Se puede hacer usando la frmula:
mid = (top + bot) /2
En este ejemplo, considere que el nmero de elementos, n es 9. Entonces el valor de
bot es 8, y el valor de mid es:
(0 + 8) / 2 = 4
Si el nmero de elementos fuese 10 y bot fuese 9, el valor de mid ser fijado en 4,
como resultado de la divisin entera.
Paso 5: Verificar si el elemento a buscar es igual al elemento en mid. Si es as,
entonces tomar la accin apropiada. Ir al paso 8.
Paso 6: Si el elemento a buscar no es igual al elemento en mid, verificar si este es
menor que el elemento en mid. Si es as, entonces en la mitad superior del arreglo
ser necesario hacer la bsqueda. Fije un nuevo valor a bot, as:
bot = mid 1
Si el elemento a buscar es mayor que el elemento en mid, entonces ser necesario
hacer la bsqueda en la mitad inferior del arreglo. Fije un nuevo valor a top, as:
top = mid + 1;
En todos los casos, se ha reducido el nmero a la mitad el nmero de elementos a
comparar.
Paso 7: Verificar s top > bot. Si es cierto, entonces el elemento a buscar no se
encontr. Tomar la accin apropiada. Si es falso, entonces ir al paso 4.
Paso 8: Fin del algoritmo.
Del algoritmo presentado anteriormente, note que los valores de top y mid van
cambiando durante el proceso de bsqueda, basados en el elemento a buscar y el
elemento en mid. Mientras que top sea menor o igual a bot, la bsqueda contina.
top llegar a ser ms grande que bot ya sea cuando el valor de bot alcance 1, o
cuando el valor de top alcance n.

A fin de comprender este algoritmo, considere tres arreglos un arreglo de palabras y


dos arreglos de enteros. La instantnea del resultado del algoritmo de bsqueda binaria
en los tres arreglos se muestra en las Figuras 5.1, 5.2, y 5.3. Se asume que el arreglo
ya est ordenado usando uno de los algoritmos aprendidos en la Unidad 3: Tcnicas de
Ordenamiento Simple.

La Figura 5.1 muestra una bsqueda exitosa. El elemento a buscar es method.

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 262

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Figura 5.1: Bsqueda Exitosa Usando el Algoritmo de Bsqueda Binaria

Puesto que el valor de mid paragraph no es igual al elemento a buscar method, y el


elemento a buscar es menor que el elemento mid, la bsqueda contina en la primera
mitad de la lista, con el valor de mid fijado al elemento explanation. El nuevo
valor de bot es ahora 6. De nuevo, el elemento mid con valor explanation no es
igual al elemento a buscar. Repitiendo el proceso, se encuentra el elemento a buscar
method, cuando este es igual al elemento en mid. En la figura, en cada etapa partes
del arreglo no han sido resaltadas, para indicar que esa parte no se considera en la
bsqueda de esa etapa.

Una bsqueda binaria cumple con la tarea de encontrar un elemento ms rpidamente


que una bsqueda lineal, dado que esta no verifica cada elemento en la lista.

Para ms ejemplos de bsqueda binaria, ver las Figuras 5.2 y 5.3. Use el algoritmo
dado anteriormente para comprender estos ejemplos claramente. Recorrer el algoritmo,
cambiando los valores de mid, top y bot para todas las iteraciones. Los valores de
mid, top y bot despus de cada iteracin se muestran claramente en las figuras.

Figura 5.2 muestra una bsqueda sin xito, donde el elemento a buscar es 200.

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 263

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Figura 5.2: Primer Ejemplo de una Bsqueda sin xito

El valor de bot finalmente alcanza1, y la condicin top > bot llega a ser cierta.

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 264

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

La Figura 5.3 tambin muestra una bsqueda sin xito, donde el elemento a buscar es
100007.

Figura 5.3: Segundo Ejemplo de Bsqueda sin xito

En este ejemplo, el valor de bot finalmente alcanza a n, y la condicin top > bot
llega a ser cierta.

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 265

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

A continuacin se presenta cmo escribir un programa en C para la bsqueda binaria.

3.1 Programa para la bsqueda binaria

El cdigo C empieza aqu...


1. int binarySearch(Element_type *elements, int n, \
2. Element_type element) {
3. int top, bot, mid, found;
4.
5. top = 0;
6. bot = n-1;
7.
8. found = 0;
9. while (top <= bot && !found) {
10. mid = (top + bot)/2;
11. if (elements[mid] == element)
12. found = 1;
13. else
14. if (element > elements[mid])
15. top = mid +1;
16. else
17. bot = mid -1;
18. }
19. return found;
20. }
EL cdigo C termina aqu

Se deben hacer los siguientes dos cambios en programa main:


Ordenar el arreglo de entrada.
Invocar la funcin binarySearch en lugar de linearSearch
La bsqueda binaria se ejecuta como sigue:

Elemento a buscar200:
Nmero de elementos en la bsqueda: 18
Elementos del arreglo:-100 -4 0 30 30 81 100 101
200 467
3213 43555 50000 60000 90000 100001 100006

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 266

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Al comienzo del ciclo: top = 0, bot = 17, mid = 8


Elemento -200 es menor que element[8] y el nuevo bot = 7

Al comienzo del ciclo: top = 0, bot = 7, mid = 3


Elemento -200 es menor que element[3] y el nuevo bot = 2

Al comienzo del ciclo: top = 0, bot = 2, mid = 1


Elemento -200 es menor que element[1] y el nuevo bot = 0

Al comienzo del ciclo: top = 0, bot = 0, mid = 0


Elemento -200 es menor que element[0] y el nuevo bot = -1

Al final del ciclo: top = 0, bot = -1, mid = 0


Elemento -200 no se encuentra en el arreglo

La bsqueda binaria del elemento 100007 en el mismo arreglo se ejecuta como sigue:
Elemento a buscar 100007:
Nmero de elementos en la bsqueda: 18
Elementos del arreglo:-100 -4 0 30 30 81 100 101
200 467
2001 3213 43555 50000 60000 90000 100001 100006

Al comienzo del ciclo: top = 0, bot = 17, mid = 8


Elemento 100007 es mayor que element[8] y el nuevo top = 9

Al comienzo del ciclo: top = 9, bot = 17, mid = 13


Elemento 100007 es mayor que element[13] y el nuevo top =
14

Al comienzo del ciclo: top = 14, bot = 17, mid = 15


Elemento 100007 es mayor que element[15] y el nuevo top =
16

Al comienzo del ciclo: top = 16, bot = 17, mid = 16


Elemento 100007 es mayor que element[16] y el nuevo top =
17

Al comienzo del ciclo: top = 17, bot = 17, mid = 17


Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 267

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Elemento 100007 es mayor que element[17] y el nuevo top =


18

Al final del ciclo: top = 18, bot = 17, mid = 17


Elemento 100007 no se encuentra en el arreglo

La bsqueda binaria del elemento 30 en el mismo arreglo se ejecuta como sigue:


Elemento a buscar 30:
Nmero de elementos en la bsqueda: 18
Elementos del arreglo:-100 -4 0 30 30 81 100 101
200 467
2001 3213 43555 50000 60000
90000 100001 100006

Al comienzo del ciclo: top = 0, bot = 17, mid = 8


Elemento 30 es menor que element[8] y el nuevo bot = 7

Al comienzo del ciclo: top = 0, bot = 7, mid = 3


Elemento 30 es equivalente a element[3]

Al final del ciclo: top = 0, bot = 7, mid = 3


Elemento 30 se encuentra en el arreglo
3.2 Comparacin entre las Tcnicas de Bsqueda Lineal y Binaria

Ambos procedimientos de bsqueda lineal y binaria tienen sus ventajas y desventajas.


Se compararn los dos procedimientos en trminos de eficiencia al realizar la
bsqueda.

En la bsqueda lineal, no es posible conocer de antemano el nmero de comparaciones


que sern realizadas antes que se encuentre el elemento de bsqueda.

Suponga que el elemento que se busca est en la primera posicin. En tal caso, solo se
realiza una comparacin antes de encontrar el elemento. Si el elemento que se est
buscando est en la segunda posicin, entonces se necesitan dos comparaciones antes
de encontrar el elemento.

Similarmente, si el elemento que se est buscando est en la posicin n-sima, se


requieren n comparaciones. As, en el peor caso, ejecutando n comparaciones se
puede encontrar al elemento buscado en la posicin n de la lista. Se puede decir que la
bsqueda no ha tenido xito, slo si el elemento buscado no es encontrado despus de
las n comparaciones.
Unidad 7: Tcnicas de Bsqueda
Libro 1: Estructura de Datos y Algoritmos 268

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

La bsqueda binaria, por otro lado, es ms rpida que la bsqueda lineal, dado que en
cada comparacin se reduce el tamao de bsqueda a la mitad. Suponga que el
nmero de elementos en el arreglo es 16, y no se encuentra el elemento que coincida
en la primera comparacin. La bsqueda binaria prosigue dividiendo el arreglo en otros
ms pequeos de ocho, cuatro, dos y finalmente un elemento.
As, si el nmero de elementos fuera n, se divide el arreglo en otros conteniendo n/2,
n/4, n/8, n/16, y as sucesivamente elementos. En cada arreglo se hacen dos
verificaciones.
Para n = 32, en lugar de hacer 32 comprobaciones para una bsqueda sin xito, se
harn solamente 6*2 = 12 verificaciones. En todos, solamente se verifican seis
arreglos:
Arreglo con 32 elementos
Arreglo con 32/2 elementos
Arreglo con 32/4 elementos
Arreglo con 32/8 elementos
Arreglo con 32/16 elementos
Arreglo con 32/32 elementos
De esta forma, es claro que la bsqueda binaria es ms rpida que la lineal.

Si embargo, la mayor limitacin de la bsqueda binaria es que el arreglo debe estar


ordenado antes. Esto puede ser demasiado costoso, especialmente para un arreglo en
el cual se hacen inserciones con mucha frecuencia.

Ahora se aprender otro mtodo de bsqueda que usa tablas hash y hashing.

4. Tablas Hash
Una tabla hash es una estructura de datos que proporciona un mtodo rpido y ms
eficiente para buscar los elementos de un arreglo. Para entender la importancia de una
tabla, considere la siguiente lista de palabras:
complexity
tree
node
while
method
sentence
rephrased
wrong
dictionary
word

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 269

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

explanation
probing
binary
linear
paragraph
Imagine encontrar el elemento linear realizando una sola verificacin, o un par de
verificaciones sin ordenar o dividir. Esto es posible si se hace corresponder (map) cada
elemento a un nico entero, el cual acta como valor ndice del arreglo donde la palabra
se encuentra. Por ejemplo, si linear se hace corresponder a 12 (por algn mtodo),
entonces se encontrar a linear simplemente diciendo word[12], donde word es
un arreglo de palabras.

Si se adapta este mtodo para una aplicacin que requiera bsqueda extensiva, el
arreglo en tal aplicacin se conoce como tabla hash, y los mtodos usados para hacer
corresponder los valores clave en la tabla hash se denominan funciones hash o
hashing. Usando funciones hash, se puede llegar a una localidad especfica, como 207,
para el primer elemento encontrado en la lista de entrada. No importa donde el
elemento est guardado en la tabla hash con tal de que se pueda encontrar fcilmente
el elemento. El valor regresado por una funcin hash se le conoce como valor hash.

Las tablas hash se definen de tamao grande, de modo que se pueda representar un
rango grande de ndices. Para almacenar 1000 enteros en una tabla hash se puede
definir la tabla hash de un tamao de 10000 enteros, as los valores hash pueden variar
entre 0 a 9999.

Se tomar un ejemplo para comprender cmo las tablas hash y hashing mejoran el
tiempo de bsqueda. La funcin hash que se elegir ser la siguiente:
Nmero de caracteres en la palabra * valor ASCII del
primer carcter
Aplicando la funcin hash en cada palabra se obtienen los valores hash, como se
muestran a continuacin:
complexity 990 10 * 99 = 990
tree 464 4 * 116 = 464
node 440 4 * 110 = 440
while 595 5 * 119 = 595
method 654 6 * 109 = 654
sentence 920 8 * 115 = 920
rephrased 1026 9 * 114 = 1026
wrong 595 5 * 119 = 595
dictionary 1000 10 * 100 = 1000
word 476 4 * 119 = 476

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 270

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

explanation 1111 11 * 101 = 1111


probing 784 7 * 112 = 784
binary 588 6 * 98 = 588
linear 648 6 * 108 = 648
paragraph 1008 9 * 112 = 1008
Las palabras estarn representadas en una tabla hash, como se muestra en la Figura
5.5.

Figura 5.5: Tabla Hash de Palabras

La Figura 5.5 bosqueja una lista parcial de palabras. Se notan dos aspectos importantes
en la tabla hash:
El orden de almacenamiento en la tabla hash de ninguna manera es similar al
orden de entrada de las palabras. La primera palabra de la tabla hash es

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 271

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

almacenada en la posicin 440, la cual es el tercer elemento de la lista de


entrada.
Dos palabras tienen el valor hash de 595. Cuando dos o ms palabras
corresponden (map) a la misma posicin despus de aplicar la funcin hash, se
conoce como una colisin.
Una forma de evitar valores hash de colisin es usar funciones hash que minimicen las
colisiones. Si las colisiones ocurren a pesar del esfuerzo, se debe tener una buena
estrategia que maneje las colisiones. Se aprender acerca de esto en la seccin
mtodos de resolucin de colisiones.

Ahora se ver cmo insertar un elemento en la tabla hash.

4.1 Insercin en una tabla Hash

Para calcular el valor hash de un elemento, la funcin hash se aplica al elemento que
ser insertado. El valor hash apunta a uno de los valores ndices del arreglo definido. Si
esa posicin en la tabla est vaca, entonces el elemento es insertado en esa posicin.
Si la posicin no est vaca, esto implica que una colisin ha ocurrido. Esta colisin
debe ser resuelta antes de ser insertado el elemento en la tabla hash. Se puede usar
una funcin rehash para resolver la colisin.

Por ejemplo, una simple funcin rehash retornar un valor mayor que aquel valor hash
obtenido cuando la colisin ocurri. As, en el ejemplo, si el valor rehash retorna 595 +
1 = 596, entonces la segunda palabra wrong, con valor hash 595, ser almacenada
en la posicin 596 en la tabla hash. La funcin rehash se usa slo cuando una posicin
especfica se encuentra ocupada.

Se aprender ms acerca de funciones rehash ms adelante en esta unidad.

4.2 Bsqueda en una Tabla Hash

El proceso de localizar un elemento en la tabla hash es similar a la funcin de insercin.


Utilizando la funcin hash y el elemento que se necesita recuperar desde la tabla hash,
se calcula el valor hash. As, nuevamente, se apunta a uno de los valores del ndice del
arreglo definido para representar la tabla hash. Se puede verificar la posicin del arreglo
indicado por el valor Hash del elemento. Si el elemento es encontrado en la posicin,
entonces el proceso de recuperacin tiene xito. Si la posicin es no vaca, pero no
contiene el elemento que se est buscando, entonces el elemento podra estar en otra
posicin del arreglo debido a la resolucin de colisin hash durante la insercin. Es
necesario resolver la colisin cuanto antes e incluso si al visitar cada posicin de la
tabla Hash no se encuentra el elemento, la bsqueda no es exitosa. Esto completa un
ciclo de verificacin de cada elemento en la tabla hash. La eliminacin de un elemento
de una tabla hash, por otro lado, simplemente requiere fijar el valor de la posicin
seleccionada en la tabla hash a un valor nulo o algn otro valor de inicio.

Ahora se aprender acerca de algunas funciones hash y acerca de la correcta seleccin


de la funcin para una aplicacin.
Unidad 7: Tcnicas de Bsqueda
Libro 1: Estructura de Datos y Algoritmos 272

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

5. Diferentes Funciones Hash


Como se ha aprendido, una funcin hash hace corresponder (map) un conjunto de
valores clave a un conjunto de ndices o direcciones. Suponga que se conocen todos
los valores claves y las direcciones a priori, entonces es ms fcil seleccionar la
correcta funcin hash. En esta situacin, los principales criterios para seleccionar una
funcin hash son los siguientes:
Debe ser simple y fcil de calcular La funcin hash seleccionada debe ser
simple y adems no contar con algn mtodo complejo o frmula compleja de
clculo. Tambin, el clculo debe ser muy rpido. Se debe recordar que en una
computadora, las operaciones de suma y resta se ejecutan mucho ms rpido
que la multiplicacin y divisin. Las operaciones de desplazamiento de bits
operan ms rpido que las operaciones aritmticas. Se debe hacer una
seleccin adecuada de las operaciones que formarn parte de la funcin.
Debe tener una funcin de correspondencia uno-a-uno - La funcin hash
seleccionada debe hacer corresponder (map) cada valor clave en un dominio a
un nico ndice o direccin en el rango de los ndices de una tabla hash. Tal
funcin, si est disponible, evitar absolutamente las colisiones, y por lo tanto,
es muy deseable.
Hay algunas dificultades en disear tales funciones hash. Es poco realista esperar
conocer todos los valores claves de antemano, as como los ndices o direcciones.
Adicionalmente, una funcin que cuenta con una funcin de correspondencia uno-a-
uno puede que no exista.

Normalmente, se trabaja con funciones que proporcionan funciones de


correspondencia muchos-a-uno. Es decir, pueden ocurrir colisiones. Por consiguiente,
el segundo criterio citado, debe ser modificado como sigue:
Las funciones hash, preferiblemente, deben dar como resultado una
distribucin uniforme de ndices/direcciones: La funcin hash seleccionada
debe lograr una distribucin uniforme de direcciones con el menor nmero de
colisiones. Es este criterio realizable? S. Se puede hacer uso de algn mtodo
general para construir funciones hash que logren uniformidad en la distribucin y
permitir un nmero mnimo de colisiones. Algunos de estos mtodos son:
- El mtodo de divisin modular.
- El mtodo de multiplicacin.
- El mtodo mid-square.
- El mtodo de Plegado (Folding).
En breve se discuten cada uno de estos mtodos.

5.1 Mtodo de Divisin Modular

En este mtodo, el primer paso es obtener un entero a partir de la clave usando un


mtodo apropiado, si la clave no es ya un entero. Se puede usar algn mtodo para

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 273

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

convertir la clave en un entero. El prximo paso es ejecutar la siguiente funcin hash


usando divisin modular:

Hash(key) = key modulo m

Asuma que m ser 25. Considere los valores claves 2546, 128, 250 y 32767. El
resultado de aplicar la funcin hash se muestra a continuacin:
2546 modulo 25 = 21
128 modulo 25 = 3
250 modulo 25 = 0
32767 modulo 25 = 17
Aqu se pueden aprender algunas cosas.
Todos los valores claves se consiguen al hacer correspondencia (map) en el
intervalo 0 a 24.
Si se desea que la funcin hash haga corresponder valores en el intervalo [1,25],
entonces lo que debe hacerse es definir la funcin como
Hash(key) = (key modulo m) + 1
Usualmente, se usan enteros positivos en este tipo de funcin hash.
Si se quiere que la funcin hash haga corresponder a valores en un amplio rango,
entonces el valor de m debe ser alto. Pero escogiendo valores grandes no es suficiente.
Por ejemplo, si se selecciona un nmero tal como 24000, este no cumplir las otras
propiedades de una buena funcin hash. Especialmente, 24000 es divisible por 2, 4, 6,
8, etc. Los cuales son enteros pequeos. Por lo tanto, se espera que un gran nmero de
claves correspondan (map) a 0 1, y como resultado, ocurrir una gran cantidad de
colisiones.

Cmo se puede evitar esto? Se puede seleccionar un nmero primo grande. Dado que
un nmero primo no es divisible por ningn otro nmero que no sea el mismo y 1,
usando un nmero primo se reduce el nmero de colisiones.

Este mtodo es eficiente en cierta medida, por que es simple. Sin embargo, involucra
divisin, la cual no es tan eficiente como la suma, diferencia o desplazamiento de bit. Se
puede usar desplazamiento de bit, por que el desplazamiento de 1 bit de un entero a la
derecha es equivalente a dividir el nmero por 2. En este caso, m debe estar expresado
en potencias de 2. Si embargo, si m es expresado en potencias de 2, este ser un
nmero no primo y inevitablemente resultar en un nmero alto de colisiones.
Claramente, hay una decisin entre eficiencia y colisin al escoger el nmero.

5.2. Mtodo de Multiplicacin

El mtodo de multiplicacin involucra los siguientes pasos:


Primero seleccionar un nmero real k como constante que est en el intervalo 0
a 1, tal que no est demasiado cerca a 0 1.
Unidad 7: Tcnicas de Bsqueda
Libro 1: Estructura de Datos y Algoritmos 274

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Luego se calcula el valor fraccional de key*k;es decir, se multiplica la clave (el


cual es un entero) por k, resultando en nmero real. Obtener slo la parte
fraccionaria. Se llamar a sta fractional_part.
Ahora, si debe hacer corresponder (map) la clave en el intervalo 0 a m, se
selecciona m, y entonces se obtiene la parte entera de la expresin
m* fractional_part. Esto dar un valor entre 0 y m.
Este ser el valor de la correspondencia.
Basados en el conjunto de pasos, se puede escribir la funcin hash como sigue:
Hash(key) = Integer_part(Fraction_part(k*key))*m)
Ahora, reconsidere el ejemplo anterior. Para simplificar, seleccionar el valor de k como
.4. El valor hash ser calculado como sigue:
Para key = 2546
k*key = 0.4*2546 = 1018.4
Fractional_part = 0.4
Fractional_part*m = 25*0.4 = 10.0
Integer_part = 10, que es el valor hash
Para key = 128
k*key = 0.4*128 = 51.2
Fractional_part = 0.2
Fractional_part*m = 25*0.2 = 5.0
Integer_part = 5, que es el valor hash
Para key = 250
k*key = 0.4*250 = 1000.0
Fractional_part = 0.0
Fractional_part*m = 25*0. = 0.0
Integer_part = 0 que es el valor hash
Para key = 32767
k*key = 0.4*32767 = 13106.8
Fractional_part = 0.8
Fractional_part*m = 25*0.8 = 20.0
Integer_part = 20, que es el valor hash
Esta eleccin de k es slo para facilitar la ilustracin. Generalmente, el k que se elige
ser una fraccin con un nmero mayor de dgitos, como 0.35433 y no una simple
fraccin como 0.4.

Este mtodo asegura que cada bit de la clave esta involucrada en la transformacin del
valor hashed entre 0 y m. Esta es una caracterstica deseable. Se sabe ahora cmo
seleccionar m desde el mtodo de divisin modular. Para seleccionar k, se debe
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 275

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

encontrar primero el nmero de bit usados para representar enteros en la computadora.


Asuma que x bits se usan para representar enteros. En este caso, k se debe escoger
de tal forma que cumpla las dos condiciones siguientes:

La parte entera de (2x)*k es relativamente primo de 2x. Lo que significa que los nicos
divisores comunes de (2x)*k y 2x son 1, y ellos mismos.
El valor de k no debe estar muy cerca de 0 1.

A continuacin se estudia el mtodo mid-square.

5.3. El Mtodo Mid-Square

El mtodo mid-square involucra los siguientes pasos:


El valor clave se multiplica por si mismo, esto es, se calcula clave2.
Luego, se elimina un cierto nmero de dgitos desde el final del nmero hasta el
resultado en el valor hash. El nmero exacto de dgitos que se van a eliminar
desde el final, depende del rango al que la funcin hash debe hacer
corresponder (map). Si la funcin hash debe hacer corresponder (map) un rango
de dos dgitos, entonces debe eliminar tantos dgitos desde el final, hasta dejar
slo dos dgitos. Similarmente, si el rango debe ser de cuatro dgitos, se debe
eliminar tantos dgitos del final hasta dejar cuatro dgitos.
Hash(key) = delete_digits_from_ends(key2)
Asuma que se da a m el valor 25. De nuevo considere los valores clave 2546, 128, 250 y
32767. Asuma que se quieren valores hash de dos dgitos. Seleccione el tercero y
cuarto digito desde la derecha del cuadrado del valor clave.
Para key = 2546
Key2 = 25462 = 6482116
Dgitos eliminados = 648 y 16
Valor Hash = 21
Para key = 128
Key2 = 1282 = 16384
Dgitos eliminados = 1 y 84
Valor Hash = 63
Para key = 250
Key2 = 2502 = 62500
Dgitos eliminados = 6 y 00
Valor Hash = 25
Para key = 32767
Key2 = 327672 = 1073768289
Dgitos eliminados = 107376 y 89

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 276

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Valor Hash = 82
Note que se podra haber seleccionado cualquier mtodo para eliminar los de dgitos
desde cualquiera de los extremos para conseguir el valor hash. Pero una vez que los
dgitos a ser eliminados son seleccionados (o los dgitos a seleccionarse para los
valores hash son seleccionados). La misma regla debe ser aplicada a todos los valores
claves. Estudios empricos muestran que el mtodo mid-square es el ms pobre, ya que
no consigue igual distribucin de claves. Debido a esta deficiencia, este mtodo es poco
usado.

A continuacin se discute el ltimo mtodo, conocido como mtodo de Plegado


(Folding).

5.4. Mtodo de Plegado (Folding)

El mtodo de Plegado (Folding) involucra los siguientes pasos:


Considere el valor clave entero. Dividir la clave en varias partes, tal que cada
parte tenga el mismo nmero de dgitos, excepto, posiblemente, una de las
partes. Por ejemplo, considere la clave 2546. Se puede dividir sta en dos
partes, 25 y 46. La eleccin de como fraccionar la clave en varias partes,
depende del rango de direcciones hash dentro del cual se har la
correspondencia (map). Si la clave 2546 se va a corresponder a una direccin
de dos dgitos, se puede dividir la clave en dos partes, cada una con dos
dgitos.
Las partes fraccionadas individuales se suman.
El resultado se toma como la clave hash. A veces, el resultado puede tener
dgitos adicionales. En ese caso, se omiten los dgitos adicionales de direccin.
Por dgitos de direccin se entiende a los que estn ms a la izquierda.
Hash(key) = key1 + key2 + + keyn
Asuma el valor de m como 25. Nuevamente, se consideran los valores claves 2546, 128,
250 y 32767. Asuma que se quieren valores hash de dos dgitos.
Para key = 2546
La clave (key) es fraccionada entre 25 y 46
Partes sumadas = 25 + 46 = 71
Valor Hash = 71
Para key = 128
La clave (key) es fraccionada entre 12 y 8 (Note que una parte
tiene slo un dgito)
Partes sumadas = 12 + 8 = 20
Valor Hash = 20
Para key = 250
La clave (key) es fraccionada entre 25 y 0

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 277

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Partes sumadas = 25 + 0 = 25
Valor Hash = 25
Para key = 32767
La clave (key) es fraccionada entre 32, 76 y 7 (Note que se
tienem tres partes)
Partes sumadas = 32 + 76 + 7 = 115
Se omiti un dgito de direccin, es decir, 1
Valor Hash = 15
En algunas versiones del mtodo de Plegado (Folding), en cada una de las partes
fraccionadas sus dgitos primero son invertidos antes de ser sumados. Por ejemplo, en
el caso de la clave 32767, se tienen las partes 32, 76 y 7. La parte par incluida es 76.
Se invierte a 67. Incluso la otra parte par, 32, se invierte a 23. La suma de las partes da
23 + 67 + 7 = 97. Dejando igual la parte de 1 dgito, se tiene el valor hash como 97.

Se han estudiado cuatro funciones hash. Se pueden construir otras funciones tambin.
Pero la mayor parte de las funciones no evitan las colisiones. A continuacin se
estudian los mtodos de resolucin de colisiones.

6. Mtodos de Resolucin de Colisiones


Como se ha visto, una mala construccin de la funcin hash puede hacer corresponder
(map) a ms de un valor clave el mismo ndice de la tabla, resultando en colisiones.
Descubrir una funcin de correspondencia (map) uno-a-uno en la funcin hash es muy
difcil, y en algunos casos casi imposible. Las colisiones ocurren con la mayor parte de
las funciones hash, es esencial tener un mtodo para resolver colisiones cuando estas
ocurran.

Cuando se utilizan arreglos de posiciones contiguas para almacenar la tabla, se pueden


emplear varios mtodos de resolucin de colisiones. De los muchos mtodos que estn
disponibles, se discuten dos en esta unidad:
Anlisis Lineal (Linear Probing).
Anlisis Cuadrtico (Quadratic Probing).
6.1 Anlisis Lineal (Linear Probing)

Considere una tabla conteniendo 15 ubicaciones, donde se planea almacenar algunas


palabras. Asuma que se tienen que almacenar las siguientes palabras:
Tree
Node
While
Method
Sentence
Dictionary

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 278

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Word
Binary
Linear
Probe
Tambin asuma que se escogi la funcin hash correcta, as como los supuestos
valores hash con respecto a cada una de las palabras mencionadas anteriormente.
Tree 2
Node 7
While 11
Method 2
Sentence 6
Dictionary 1
Word 11
Binary 4
Linear 14
Probe 9
Note que hay dos colisiones aqu. Las palabras Tree y Method tienen valores hash de
2. Similarmente, las palabras While y Word tienen el mismo valor hash, 11.
Claramente, no se pueden poner Tree y Method en la misma posicin de la tabla. La
palabra Tree viene a ser la primera, as sta es colocada en la posicin 2 de la tabla.
Entonces, las otras palabras se colocan en la tabla, hasta que se alcance la palabra
Method. En este punto, la tabla luce como se muestra a continuacin.
1 -
2 Tree
3 -
4 -
5 -
6 -
Nod
7
e
8 -
9 -
1
-
0
1 Whil
1 e
1
-
2
1
-
3
1 -
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 279

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

4
1
-
5
Dado que Tree est en la posicin 2, no se puede colocar Method all. El mtodo
anlisis lineal (linear probing) busca ms all de la posicin hasta una posicin libre. En
esta tabla, la posicin 3 est libre. As, se puede colocar Method all. Las otras palabras
en la lista pueden ser colocadas en la tabla usando este mtodo de resolucin de
colisiones. Se muestra la tabla final despus de haber colocado todas las palabras.
Dictionar
1
y
2 Tree
3 Method
4 Binary
5 -
Sentenc
6
e
7 Node
8 -
9 Probe
1
-
0
1
While
1
1
Word
2
1
-
3
1
Linear
4
1
-
5
Note como la colisin de While y Word son manejadas por anlisis lineal (linear
probing).

Este mtodo tiene algunas desventajas. Asuma que la tabla est llena. Entonces, as se
irn insertando valores en la tabla a travs de anlisis lineal (linear probing), basados en
la ocurrencia de las colisiones, se descubrir que hay una tendencia de los registros a
agruparse juntos. El agrupamiento no es deseable, dado que esto indica que las claves
no estn distribuidas uniformemente.

Un mtodo para evitar el agrupamiento (clustering) es rehashing. En este mtodo,


cuando una colisin ocurre, se calcula una segunda funcin hash. La posicin de la
clave ser dada por el valor calculado de la segunda funcin hash, por consiguiente se
realiza el rehashing. Por ejemplo si la funcin hash es:
key value % SIZEOFARRAY
Unidad 7: Tcnicas de Bsqueda
Libro 1: Estructura de Datos y Algoritmos 280

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

La funcin rehash puede ser:


(key value + 1) % SIZEOFARRAY
Si SIZEOFARRAY es 100 y el valor de la clave es 10908, la funcin hash retorna
10908 % 100 = 8 y la funcin rehash retorna (10908 + 1) % 100 = 9.

Otro mtodo que evita el agrupamiento (clustering) es el de determinar cun lejos desde
el punto de la colisin se mantendr este registro. Esto puede ser dado por una funcin
increment. No se entrar en detalles sobre la funcin increment en este curso. As con
rehashing, la funcin increment se calcula cuando ocurre una colisin y determina la
nueva posicin.

Ambos mtodos trabajan con un grado de xito limitado en tablas grandes. La debilidad
del anlisis lineal (linear probing) es que requiere hacer pruebas secunciales para
determinar la prxima ubicacin libre. Cuando algunas claves hacen corresponder
(map) a la misma ubicacin, esto llega a ser una desventaja.

A continuacin se discute el segundo mtodo para resolver colisiones, el anlisis


cuadrtico (quadratic probing).

6.2 Anlisis Cuadrtico (Quadratic probing)

En el anlisis lineal (linear probing), se prueban secuencialmente las posiciones de la


tabla hash. Por ejemplo, si la colisin ocurre en la posicin x, se prueban x+1, x+2,
x+3, x+4, etc. En el anlisis cuadrtico (quadratic probing), se prueban las posiciones
x+1, x+4, x+9, x+16 y as en adelante, etc. Generalizando esto, se puede decir que
sta es x + i2 donde i vara desde 1 a n. Para comprender este mtodo, considere
las siguientes palabras con sus valores hash:
Tree 2
Node 7
While 11
Method 2
Sentence 7
Dictionary 11
Word 11
Binary 4
Linear 14
Probe 9
Con el anlisis cuadrtico (quadratic probing), las palabras sern asignadas a la tabla
como sigue:
1 -
2 Tree
3 Method x+1
4 Binary
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 281

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

5 -
6 -
7 Node
Sentenc x+1
8
e
9 Probe
1
-
0
1
While
1
1 Dictionar x+1
2 y
1
-
3
1
Linear
4
1 x+4
Word
5
Es necesario sealar el valor probado antes de insertarlo en la tabla hash.

El mismo conjunto de palabras con el anlisis lineal (linear probing) resulta en lo


siguiente:
1 -
2 Tree
3 Method x+1
4 Binary
5 -
6 -
7 Node
Sentenc x+1
8
e
9 Probe
1
-
0
1
While
1
1 Dictionar x+1
2 y
1 x+2
Word
3
1
Linear
4
1
-
5

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 282

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Quadratic probing es superior a Anlisis Lineal (Linear probing), dado que reduce el
agrupamiento (clustering). Observe que las palabras While, Dictionary, Word y
Linear son agrupadas en la tabla de anlisis lineal. Por lo tanto, con el anlisis
cuadrtico (quadratic probing) se prueban menos posiciones.

Hay algunas otros mtodos de resolucin de colisiones, algunos de los cuales son muy
sofisticados. La discusin de estos mtodos va ms haya del alcance de este curso.

6.3 Algunas Operaciones en Tablas Hash

Ahora considere la implementacin de algunas operaciones en las tablas hash. La


declaracin de una tabla hash se presenta a continuacin.

El cdigo C empieza aqu...


1. #include <stdio.h>
2. #include <stdlib.h>
3.
4. #define MAXSIZE 10000
5.
6. typedef int Element_type;
7.
8. typedef struct node {
9. Element_type element;
10. struct node *next;
11. } Node_type;
12. typedef Node_type *HashTable_type[MAXSIZE];
El cdigo C termina aqu

Para inicializar una tabla hash, se puede usar la siguiente operacin:

El cdigo C empieza aqu...


1. /* Funcin para inicializar la tabla hash */
2. void initHashTable(HashTable_type hashTable) {
3. int i;
4. for (i = 0; i < MAXSIZE; i++)
5. hashTable[i] = NULL;
6. }
El cdigo C termina aqu

Las funciones hash y rehash se implementan como simples funciones que usan
aritmtica modular.
Libro 1: Estructura de Datos y Algoritmos
Unidad 7: Tcnicas de Bsqueda 283

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

El cdigo C empieza aqu...


1. /* La funcin hash */
2. int hash(int key) {
3. return (key % MAXSIZE);
4. }
5. /* La funcin rehash */
6. int rehash(int key) {
7. return ((key + 1) % MAXSIZE);
8. }
El cdigo C termina aqu

A continuacin se presenta una funcin que obtiene un nodo.

El cdigo C empieza aqu...


1. /* Funcin que obtiene un nodo */
2. Node_type * getNode(Element_type element) {
3. Node_type *node;
4. node = (Node_type *) malloc(sizeof(Node_type));
5. node->element = element;
6. node->next = NULL;
7. return node;
8. }
El cdigo C termina aqu

La siguiente funcin ayuda a insertar elementos en la tabla hash. Note cmo la funcin
rehash se utiliza repetidamente para obtener el ndice de la tabla donde est
almacenado el elemento.

El cdigo C empieza aqu...


1. /* Funcin para insertar en la tabla hash */
2. void insert(HashTable_type hashTable, Node_type *node)
{
3. int hashValue, firstHashValue;
4.
5. hashValue = hash(node->element);
6. firstHashValue = hashValue;
7. while (hashTable[hashValue] != NULL) {
8. hashValue = rehash(hashValue);

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 284

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

9. /* Chequear si la tabla hash est llena */


10. if (hashValue == firstHashValue) {
11. printf("La tabla est llena: No puede
insertar\n");
12. return;
13. }
14. }
15. printf("El valor Hash para el elemento %d es %d\n", \
16. node->element, hashValue);
17. node->next = hashTable[hashValue];
18. hashTable[hashValue] = node;
19. }
El cdigo C termina aqu

La siguiente funcin implementar la recuperacin de un elemento de la tabla hash.

El cdigo C empieza aqu...


1. /* Funcin para recuperar elementos de la tabla hash */
2. Node_type* find(HashTable_type hashTable, \
3. Element_type element, int *index) {
4. int hashValue = hash(element);
5. int firstHashValue = hashValue;
6.
7. if (hashTable[hashValue] == NULL)
8. return NULL;
9. while (hashTable[hashValue]->element != element) {
10. hashValue = rehash(hashValue);
11. /* Si no encontr el elemento*/
12. if (hashValue == firstHashValue)
13. return NULL;
14. }
15. *index = hashValue;
16. return hashTable[hashValue];
17. }
El cdigo C termina aqu

A continuacin para ilustrar se escribe una funcin que invoca todas estas funciones.
Note que el programa no est diseado para hacer nada especfico, ms all de la tarea

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 285

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

de mostrar la manera en la que se pueda invocar a las funciones que trabajan con las
tablas hash.

El cdigo C empieza aqu...


1. main() {
2. HashTable_type hashTable;
3. Node_type *node;
4. int index;
5. Element_type element;
6. initHashTable(hashTable);
7. node = getNode(12101);
8. insert(hashTable, node);
9. node = getNode(12201);
10. insert(hashTable, node);
11. node = getNode(23101);
12. insert(hashTable, node);
13. node = getNode(12403);
14. insert(hashTable, node);
15. node = getNode(12400);
16. insert(hashTable, node);
17. node = getNode(1501);
18. insert(hashTable, node);
19. node = getNode(16541);
20. insert(hashTable, node);
21. node = getNode(121);
22. insert(hashTable, node);
23. node = getNode(1121);
24. insert(hashTable, node);
25. node = getNode(2121);
26. insert(hashTable, node);
27. node = getNode(17451);
28. insert(hashTable, node);
29. node = getNode(17541);
30. insert(hashTable, node);
31.
32. element = 11210;
33. if (find(hashTable, element, &index))

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 286

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

34. printf("Elemento %d encontrado en la posicin


%d\n",element,index);
35. else
36. printf("Elemento %d no encontrado\n",element);
37. }
El cdigo C termina aqu

La salida del programa ser la siguiente:


El valor Hash para el elemento 12101 es 2101
El valor Hash para el elemento 12201 es 2201
El valor Hash para el elemento 23101 es 3101
El valor Hash para el elemento 12403 es 2403
El valor Hash para el elemento 12400 es 2400
El valor Hash para el elemento 1501 es 1501
El valor Hash para el elemento 16541 es 6541
El valor Hash para el elemento 121 es 121
El valor Hash para el elemento 1121 es 1121
El valor Hash para el elemento 2121 es 2121
El valor Hash para el elemento 17451 es 7451
El valor Hash para el elemento 17541 es 7541
Elemento 11210 no encontrado

7. Aplicaciones de Tablas Hash


Las siguientes son algunas aplicaciones que utilizan tablas hash:
Compiladores y Ensambladores- En Compiladores y Ensambladores, existe la
necesidad de mantener las tablas de smbolos. Los compiladores que compilan
programas fuente en lenguajes de alto nivel, tales como C o Pascal, mantienen
una estructura de datos llamada tabla de smbolo. La tabla de smbolo contiene,
entre otras cosas, el smbolo en s mismo, adems de algunos atributos del
smbolo, derivados del contexto de su utilizacin en el programa. Los smbolos
que se encuentran durante la compilacin de un programa fuente son: nombres
de identificacin de variables, identificadores de constante e identificadores de
nombre de funciones, entre otros. En las tablas de smbolos, las bsquedas,
usos, adems de las modificaciones a los smbolos son frecuentes y por
consiguiente, se tiene la necesidad de tener una correspondencia (map) de
smbolo-a-valor directo. Las tablas hash proporcionan esta funcionalidad de
manera eficiente.
Aplicaciones que requieren buscar Existen numerosas aplicaciones que
requieren ejecutar una bsqueda basada en un valor clave. La bsqueda puede
ser ejecutada en un diccionario, un directorio telefnico, un catlogo de

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 287

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

productos o un ndice de un sistema de archivos en un libro. En todos estos


casos las tablas hash proporcionan un mecanismo de acceso eficiente.

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 288

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

Resumen
Ahora que Ud. ha completado esta unidad, debe ser capaz de:
Explicar las diversas tcnicas de bsqueda disponibles para operaciones en
arreglos y otras estructuras de datos.
Describir cmo desarrollar un algoritmo para la tcnica de bsqueda lineal.
Describir cmo desarrollar un algoritmo para la tcnica de bsqueda binaria.
Explicar el uso de hashing para insertar y localizar elementos en una tabla hash.
Discutir los mtodos de resolucin de una colisin hash.

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 289

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Unidad 7: Examen de Autoevaluacin


1) En cul de las siguientes condiciones ocurre una bsqueda interna?
a) Cuando todos los registros que estn siendo buscados estn en la memoria
primaria.
b) Cuando todos los registros que estn siendo buscados estn en la memoria
secundaria.

2) Cul de las siguientes puede ser llamada una bsqueda binaria?


a) Una tcnica de bsqueda que sigue un mtodo de bsqueda secuencial.
b) Una tcnica de bsqueda que involucra dividir un arreglo en mitades en cada
repeticin.
c) Ambas (a) y (b).
d) Ninguna de las anteriores.

3) Cul de las siguientes tcnicas involucra encontrar el elemento medio?


a) Bsqueda Lineal.
b) Bsqueda Binaria.
c) Hashing.
d) Todas las anteriores.

4) Para cules de las siguientes se usa hashing y funciones hash?


a) Para construir y usar archivos de texto.
b) Para construir un editor.
c) Para construir una aplicacin de hoja de clculo.
d) Para construir y usar tablas de smbolo en compiladores.

5) El orden de los elementos almacenados en una tabla hash es el mismo que el


orden de entrada de elementos.
a) Verdadero.
b) Falso.

6) El algoritmo bsico para localizar el valor de ndice en una tabla hash para
insercin y locacin de un elemento es el mismo.
a) Verdadero.
b) Falso.

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 290

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Libro 1: Estructura de Datos y Algoritmos Gua del Estudiante

7) Cul de los siguientes son mtodos para escoger una funcin hash?
a) Divisin Modular.
b) Multiplicacin.
c) De Plegado (Folding).
d) Ninguna de las anteriores.

8) Cules de los siguientes mtodos crea una parte fraccional para calcular los
valores hash?
a) Divisin Modular.
b) Multiplicacin.
c) De Plegado (Folding).
d) Mid-square.

9) Anlisis Lineal (Linear probing) es un mtodo para evitar agrupamiento.


a) Verdadero.
b) Falso.

10) El anlisis cuadrtico (Quadratic probing) es un mtodo mejor de resolucin de


colisin hash que el anlisis lineal (Linear probing).
a) Verdadero.
b) Falso.

Libro 1: Estructura de Datos y Algoritmos


Unidad 7: Tcnicas de Bsqueda 291

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Libro 1: Estructura de Datos y Algoritmos

Respuestas a la Unidad 7: Examen de Autoevaluacin


1) a
2) b
3) b
4) d
5) b
6) a
7) a, b y c
8) b
9) b
10) a

Unidad 7: Tcnicas de Bsqueda


Libro 1: Estructura de Datos y Algoritmos 292

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el permiso escrito previo de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 8: Laboratorio de Tcnicas de


Bsqueda
Objetivos de Aprendizaje
Al final de esta unidad, ud. debe ser capaz de:
Aplicar los conceptos aprendidos sobre bsqueda en cualquier esfuerzo de
desarrollo de aplicaciones.
Escribir algoritmos para bsqueda lineal y binaria.

Libro 1: Estructura de Datos y Algoritmos Unidad 8: Laboratorio de Tcnicas de Bsqueda 293

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejercicios de Laboratorio
La compaa XYZ es fabricante de partes de auto y produce millones de autopartes
todos los das. La compaa asigna un nmero de parte nico a cada parte. El nmero
de parte es alfanumrico y consiste de tres partes:
Un cdigo entero de dos dgitos indicando el tipo de carro al que pertenece la
parte.
Un cdigo de cinco letras de caracteres indicando el mes y da de la produccin.
Un cdigo entero de seis dgitos indicando un nmero de identificacin nica de
la parte producida.
Un ejemplo se presenta a continuacin:
09JUN22100056
Donde:
09 es el tipo de carro.
JUNE 22 es la fecha de produccin.
100056 es la identificacin nica de la parte fabricada el 22 de junio. La
identificacin nica va de un rango de 000000 a 999999.
La compaa, en muchos casos, requiere datos sobre todas las partes fabricadas en un
da especfico, pertenecientes a un tipo especfico de carro. Estos datos pueden ser
requeridos en orden o en desorden.

Se requiere que usted escriba un programa en C que haga lo siguiente. Asuma que los
datos son ingresados para un da y mes especfico.
1) Construya una lista de partes de carros que tengan el nmero de partes como nica
entrada en el arreglo. Para construir la lista se deben seguir los siguientes pasos a
continuacin:
a. El da y mes de la fabricacin se toma como una entrada una vez al inicio del
programa.
b. La entrada se toma para el tipo de carro y nmero de identificacin nico. El tipo
de carro debe ser ingresado como dos caracteres y la identificacin nica como
seis caracteres.
2) Mantenga un arreglo que contenga los nmeros de partes en el orden de entrada.
Imprima todos los nmeros de parte, en el orden de entrada.
3) Tomando como entrada un tipo de carro y un nmero de identificacin nico,
determine si el nmero de parte est disponible en el arreglo. Utilice una bsqueda
binaria. El orden original de entrada del nmero de partes no debe afectarse.

Unidad 8: Laboratorio de Tcnicas de Bsqueda Libro 1: Estructura de Datos y Algoritmos 294

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Consejos tiles:
Cree una estructura que contenga el arreglo de nmeros de partes y el nmero
de total de partes dado como una entrada.
Tome el da y mes de fabricacin como entrada y ejecute una validacin de la
fecha. Use el ao actual como ao. Tome la entrada del da y mes como
enteros. #define el valor. Utilice la funcin de validacin de fecha que se da a
continuacin.

// Chequear si la fecha de entrada es vlida


int isDateValid(int day, int month) {
// Asignar nmero de das a 22 para feb,
// si el ao es bisiesto
if (((YEAR % 4 == 0) && (YEAR % 100 != 0)) || \
(YEAR % 400 == 0)) {
days[2] = 29;
}

// Si el valor est fuera del rango posible


if((day < 1)||(month < 1)||(month > 12)||(YEAR < 1)) {
return 0;
}
// Si la fecha est dentro del rango del mes
if(day > days[month]) {
return 0;
}
return 1;
}

Convierta el da y el mes en un arreglo de caracteres de fecha como se muestra


a continuacin.
#define YEAR 2002
Tipo_elemento months[12][4] = {"ENE", "FEB", "MAR", "ABR",
\
"MAY", "JUN", "JUL", "AGO", "SEP", "OCT", "NOV", "DIC"};
Tipo_elemento date[DATESIZE + 1];
// Convertir da y mes en un arreglo de caracteres de fecha

Libro 1: Estructura de Datos y Algoritmos Unidad 8: Laboratorio de Tcnicas de Bsqueda 295

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

// Asignar la porcin del mes


strcpy(date, months[month-1]);
/* Almacenar el primer dgito del da dentro de la 4ta
posicin
de la fecha */
date[3] = '0' + (day / 10);
/* Almacenar el Segundo dgito del da dentro de la
5ta
posicin de la fecha */
date[4] = '0' + (day % 10);
// Almacenar carcter nulo
date[5] = '\0';

Tome la entrada del tipo de carro y el nmero de identificacin para formar el


nmero de parte usando el da y mes de produccin. Asigne en el arreglo
original. Se muestra a continuacin.
printf("\nIngrese el tipo de carro y un nmero de id nico
para \
cada parte ... enter -9!\n");
do {
printf("\nIngrese el tipo de carro: ");
scanf("%s", carType);
if (strcmp(carType, "-9")) {
printf("Ingrese Nmero de id: ");
scanf("%s", partId);
strcpy(partNumber, carType);
strcat(partNumber, date);
strcat(partNumber, partId);
printf("\nEl nmero de parte es %s\n",
partNumber);
strcpy(partNumberOriginal.partNumbers[i++],
\
partNumber);
}
// Fin de entrada de tipo de carro y nico nmero de
id
} while (strcmp(carType, "-9"));
partNumberOriginal.totalParts = i;

Unidad 8: Laboratorio de Tcnicas de Bsqueda Libro 1: Estructura de Datos y Algoritmos 296

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Imprima el arreglo original.


Copie el arreglo original en otro arreglo, elemento por elemento.
Use una de las funciones ordenadas aprendidas en la Unidad 3: Tcnicas de
Ordenamiento Simple-. Haga cambios apropiados a la funcin para trabajar con
cadenas.
Tome el tipo de carro y nmero de identificacin como entrada para la
bsqueda. Usando el algoritmo de bsqueda binaria, otra vez haga cambio
apropiados para trabajar con cadenas, encuentre el tipo de carro y el nmero de
identificacin. La manera fcil de hacer esto, es formar el nmero de parte otra
vez. Despus busque el nmero de parte en el arreglo ordenado.
Presente mensajes apropiados.

Libro 1: Estructura de Datos y Algoritmos Unidad 8: Laboratorio de Tcnicas de Bsqueda 297

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Unidad 9: Laboratorio de Tablas Hash


Objetivos de Aprendizaje
Al final de esta unidad, Ud. debe ser capaz de:
Utilizar los conceptos que ha aprendido para crear una tabla hash.
Usar tablas hash en diferentes aplicaciones.
Aplicar las tcnicas aprendidas en otras aplicaciones.

Libro 1: Estructura de Datos y Algoritmos Unidad 9: Laboratorio de Tablas Hash 299

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Estructura de Datos y Algoritmos Gua del Estudiante

Ejercicios de Laboratorio
Los compiladores que compilan programas fuente en lenguajes de alto nivel tales como
C, Pascal, etc., mantienen una estructura de datos llamada tabla de smbolos. Una de
las opciones para implementar una tabla de smbolos es a travs de tablas hash. La
tabla de smbolos contiene, entre otras cosas, el smbolo en s mismo y algunos
atributos sobre el smbolo derivado del contexto de su uso en el programa.

Los smbolos encontrados durante la compilacin de un programa fuente son nombres


de identificadores de variables, identificadores de constantes, identificadores de nombre
de funciones y as sucesivamente. Las tablas hash dan la capacidad de que para un
smbolo considerado (digamos, un nombre de identificador), la ubicacin en la tabla de
smbolos se puede derivar directamente por el clculo de una funcin hash.

Algunas de las operaciones comunes hechas en las tablas de smbolos se enumeran a


continuacin.
Crear una tabla de smbolos nueva y vaca.
Insertar una entrada en la tabla de smbolos.
Eliminar una entrada en la tabla de smbolos.
Ubicar una entrada en la tabla de smbolos.
Por supuesto, hay muchas ms operaciones posibles, pero se considerarn solamente
las mencionadas.

Tambin, en una tabla de smbolos, cuando se hace referencia a una entrada, se


refiere al smbolo y sus atributos asociados requeridos para el uso del compilador. En
este ejercicio, no se consideran los otros atributos y se pensar en una entrada slo
como el smbolo.

Escriba las siguientes funciones en C para implementar las operaciones en una tabla de
smbolos usando hashing.
createSym(s): Crea una nueva tabla de smbolos s vaca y la inicializa.
insertSym(s, x): Inserta el smbolo x en la tabla de smbolos s.
deleteSym(s, x): Elimina el smbolo x de la tabla de smbolos s, si x existe.
findSym(s, x): Encuentra la posicin del smbolo x en la tabla de smbolos s, si
existe o de otra manera devuelve un error.
Tambin, escriba un programa main que invoque las diferentes funciones para
comprobar la funcionalidad.

Consejos tiles
El smbolo de entrada debe ser un arreglo de caracteres.

Unidad 9: Laboratorio de Tablas Hash Libro 1: Estructura de Datos y Algoritmos 300

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.
Gua del Estudiante Estructura de Datos y Algoritmos

Definir un arreglo para mantener los smbolos. ste actuar como la tabla hash.
Inicializar todas las filas en la tabla hash a \0 (carcter nulo). El mismo carcter
nulo puede ser usado para cualquier otra verificacin en otro programa.
Emplee cualquier funcin hash buena. Recuerde realizar rehash si la posicin se
encuentra ocupada.
Cuando un smbolo es ingresado, usando la funcin hash, derive el valor hash y
coloque el smbolo en el arreglo en la posicin equivalente al valor hash.
Para borrar un smbolo, simplemente ponga la celda en la tabla hash a \0. El
nodo puede continuar existiendo en la lista enlazada.
Para encontrar un elemento, busque a travs de la tabla hash.

Libro 1: Estructura de Datos y Algoritmos Unidad 9: Laboratorio de Tablas Hash 301

Copyright IBM Corp. 2008


Los materiales del curso no pueden ser reproducidos total o
parcialmente sin el previo permiso escrito de IBM.

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