Sie sind auf Seite 1von 11

INTRODUCCION A ALGORITMOS

1 El papel de los algoritmos en la informática


¿Qué son los algoritmos? ¿Por qué vale la pena estudiar algoritmos? ¿Cuál
es el papel de los algoritmos en relación con otras tecnologías utilizadas en
las computadoras? En este capítulo, responderemos estas preguntas.

1.1 Algoritmos
Informalmente, un algoritmo es cualquier procedimiento
computacional bien definido que toma algún valor, o conjunto de
valores, como entrada y produce algún valor, o conjunto de valores,
como salida. Por lo tanto, un algoritmo es una secuencia de pasos
computacionales que transforman la entrada en la salida.
También podemos ver un algoritmo como una herramienta para
resolver un problema computacional bien especificado. La declaración
del problema especifica en términos generales la relación deseada de
entrada / salida. El algoritmo describe un procedimiento computacional
específico para lograr esa relación de entrada / salida.
Por ejemplo, podríamos necesitar ordenar una secuencia de números
en orden no decreciente. Este problema surge con frecuencia en la
práctica y proporciona un terreno fértil para introducir muchas técnicas
de diseño estándar y herramientas de análisis. Así es como definimos
formalmente el problema de clasificación:

Entrada: una secuencia de n números [a1; a2; : : : ;an.]


Salida: una permutación (reordenamiento) [a’1;a’2; : : : ;a’n.] de la
secuencia de entrada como eso a’1<a’2<…<a’n

Por ejemplo, dada la secuencia de entrada [31; 41; 59; 26; 41; 58], un
algoritmo de clasificación devuelve como salida la secuencia [26; 31; 41;
41; 58; 5]. Tal secuencia de entrada se llama una instancia del problema
de clasificación. En general, una instancia de un problema consiste en la
entrada (que satisface las restricciones impuestas en la declaración del
problema) necesaria para calcular una solución al problema.

Debido a que muchos programas lo usan como un paso intermedio, la


clasificación es una operación fundamental en informática. Como
resultado, tenemos una gran cantidad de buenos algoritmos de
clasificación a nuestra disposición. El mejor algoritmo para una
aplicación determinada depende, entre otros factores, de la cantidad
de elementos que se ordenarán, la medida en que los elementos ya
están clasificados, las posibles restricciones en los valores de los
elementos, la arquitectura de la computadora y el tipo de dispositivos
de almacenamiento que se utilizarán: memoria principal, discos o
incluso cintas.

Se dice que un algoritmo es correcto si, para cada instancia de entrada,


se detiene con la salida correcta. Decimos que un algoritmo correcto
resuelve el problema computacional dado. Un algoritmo incorrecto
podría no detenerse en absoluto en algunas instancias de entrada, o
podría detenerse con una respuesta incorrecta. Al contrario de lo que
cabría esperar, los algoritmos incorrectos a veces pueden ser útiles, si
podemos controlar su tasa de error. Veremos Un ejemplo de un
algoritmo con una tasa de error controlable en el Capítulo 31 cuando
estudiamos algoritmos para encontrar números primos grandes.
Normalmente, sin embargo, solo nos ocuparemos de los algoritmos
correctos.
Un algoritmo puede especificarse en inglés, como un programa de
computadora o incluso como un diseño de hardware. El único requisito
es que la especificación debe proporcionar una descripción precisa del
procedimiento computacional a seguir.

Qué tipo de problemas resuelven los algoritmos?

La clasificación no es el único problema computacional para el cual se


han desarrollado algoritmos. (Probablemente sospechó lo mismo
cuando vio el tamaño de este libro). Las aplicaciones prácticas de
algoritmos son ubicuas e incluyen los siguientes ejemplos:

El Proyecto del Genoma Humano ha hecho un gran progreso hacia los


objetivos de identificar todos los 100,000 genes en el ADN humano,
determinar las secuencias de los 3 mil millones de pares de bases
químicas que forman el ADN humano, almacenar esta información en
bases de datos y desarrollar herramientas para el análisis de datos. Cada
uno de estos pasos requiere algoritmos sofisticados. Aunque las
soluciones a los diversos problemas involucrados están más allá del
alcance de este libro, existen muchos métodos para resolverlos.
Los problemas biológicos utilizan ideas de varios de los capítulos de este
libro, lo que permite a los científicos realizar tareas mientras utilizan los
recursos de manera eficiente. Los ahorros son en tiempo, tanto
humanos como en máquinas, y en dinero, ya que se puede extraer más
información de las técnicas de laboratorio.

Internet permite a las personas de todo el mundo acceder rápidamente


y recuperar grandes cantidades de información. Con la ayuda de
algoritmos inteligentes, los sitios en Internet pueden administrar y
manipular este gran volumen de datos. Los ejemplos de problemas que
hacen un uso esencial de los algoritmos incluyen la búsqueda de buenas
rutas por las que viajarán los datos (las técnicas para resolver tales
problemas aparecen en el Capítulo 24) y el uso de un motor de
búsqueda para encontrar rápidamente páginas en las que reside la
información (las técnicas relacionadas se encuentran en los capítulos 11
y 32).

El comercio electrónico permite que los bienes y servicios se negocien


e intercambien electrónicamente, y depende de la privacidad de la
información personal, como números de tarjetas de crédito,
contraseñas y extractos bancarios. Las tecnologías centrales utilizadas
en el comercio electrónico incluyen criptografía de clave pública y
firmas digitales (cubiertas en el Capítulo 31), que se basan en algoritmos
numéricos y teoría de números.

Las empresas manufactureras y otras empresas comerciales a menudo


necesitan asignar recursos escasos de la manera más beneficiosa. Una
compañía petrolera puede desear saber dónde ubicar sus pozos para
maximizar sus ganancias esperadas. Un candidato político puede querer
determinar dónde gastar dinero comprando publicidad de campaña
para maximizar las posibilidades de ganar una elección. Una aerolínea
puede desear asignar tripulaciones a los vuelos de la manera menos
costosa posible, asegurándose de que cada vuelo esté cubierto y que se
cumplan las regulaciones gubernamentales con respecto a la
programación de la tripulación. Un proveedor de servicios de Internet
puede desear determinar dónde colocar recursos adicionales para
servir a sus clientes de manera más efectiva. Todos estos son ejemplos
de problemas que pueden resolverse mediante programación lineal,
que estudiaremos en el Capítulo 29.

Aunque algunos de los detalles de estos ejemplos están más allá del
alcance de este libro, brindamos técnicas subyacentes que se aplican a
estos problemas y áreas problemáticas. También mostramos cómo
resolver muchos problemas específicos, incluidos los siguientes:

Se nos proporciona una hoja de ruta en la que se marca la distancia


entre cada par de intersecciones adyacentes, y deseamos determinar la
ruta más corta de una intersección a otra. El número de rutas posibles
puede ser enorme, incluso si no permitimos rutas que se cruzan sobre
sí mismas. ¿Cómo elegimos cuál de todas las rutas posibles es la más
corta? Aquí, modelamos la hoja de ruta (que es en sí misma un modelo
de las carreteras reales) como un gráfico (que veremos en la Parte VI y
el Apéndice B), y deseamos encontrar la ruta más corta de un vértice a
otro en el gráfico . Veremos cómo resolver este problema de manera
eficiente en el Capítulo 24.

Se nos dan dos secuencias ordenadas de símbolos, X = {x1; x2; :::; xm} e Y
= {y1; y2; :::; yn}, y deseamos encontrar una subsecuencia común más
larga de X e Y. Una subsecuencia de X es solo X con algunos (o
posiblemente todos o ninguno) de sus elementos eliminados. Por
ejemplo, una subsecuencia de {A; B; C; D; E; F; G} sería {B; C; E; G};
Soldado americano. La longitud de una subsecuencia común más larga
de X e Y da una medida de cuán similares son estas dos secuencias. Por
ejemplo, si las dos secuencias son pares de bases en cadenas de ADN,
entonces podríamos considerarlas similares si tienen una subsecuencia
común larga. Si X tiene m símbolos e Y tiene n símbolos, entonces X e Y
tienen 2m y 2n subsecuencias posibles, respectivamente. Seleccionar
todas las subsecuencias posibles de X e Y y hacerlas coincidir podría
llevar un tiempo prohibitivamente largo a menos que m y n sean muy
pequeñas. En el Capítulo 15 veremos cómo usar una técnica general
conocida como programación dinámica para resolver este problema de
manera mucho más eficiente.
Se nos da un diseño mecánico en términos de una biblioteca de partes,
donde cada parte puede incluir instancias de otras partes, y debemos
enumerar las partes en orden para que cada parte aparezca antes de
cualquier parte que la use. Si el diseño comprende n partes, entonces
hay n! posibles órdenes, donde n! denota la función factorial. Debido a
que la función factorial crece más rápido que incluso una función
exponencial, no podemos generar de manera factible cada orden
posible y luego verificar que, dentro de ese orden, cada parte aparezca
antes que las partes que la usan (a menos que tengamos solo unas
pocas partes). Este problema es una instancia de clasificación
topológica, y veremos en el Capítulo 22 cómo resolver este problema
de manera eficiente.

Se nos dan n puntos en el plano, y deseamos encontrar el casco convexo


de estos puntos. El casco convexo es el polígono convexo más pequeño
que contiene los puntos. Intuitivamente, podemos pensar que cada
punto está representado por un clavo que sobresale de un tablero. El
casco convexo estaría representado por una banda elástica apretada
que rodea todos los clavos. Cada clavo alrededor del cual gira la banda
de goma es un vértice del casco convexo. (Consulte la Figura 33.6 en la
página 1029 para ver un ejemplo). Cualquiera de los 2n subconjuntos
de puntos podrían ser los vértices del casco convexo. Saber qué puntos
son vértices del casco convexo tampoco es suficiente, ya que también
necesitamos saber el orden en que aparecen. Hay muchas opciones, por
lo tanto, para los vértices del casco convexo. El Capítulo 33 ofrece dos
buenos métodos para encontrar el casco convexo.

Estas listas están lejos de ser exhaustivas (como probablemente haya


deducido del peso de este libro), pero exhiben dos características que
son comunes a muchos problemas algorítmicos interesantes:

1. Tienen muchas soluciones candidatas, la gran mayoría de las cuales


no resuelven el problema en cuestión. Encontrar uno que lo haga, o
uno que sea "mejor", puede presentar un gran desafío.

2. Tienen aplicaciones prácticas. De los problemas en la lista anterior,


encontrar el camino más corto proporciona los ejemplos más fáciles.
Una empresa de transporte, como una compañía de camiones o
ferrocarriles, tiene un interés financiero en encontrar caminos más
cortos a través de una red de carreteras o ferrocarriles porque tomar
caminos más cortos resulta en menores costos de mano de obra y
combustible. O un nodo de enrutamiento en Internet puede
necesitar encontrar la ruta más corta a través de la red para enrutar
un mensaje rápidamente. O una persona que desea conducir desde
Nueva York a Boston puede querer encontrar instrucciones de
manejo desde un sitio web apropiado, o puede usar su GPS mientras
conduce.

No todos los problemas resueltos por algoritmos tienen un conjunto


de soluciones candidatas fácilmente identificables. Por ejemplo,
supongamos que se nos da un conjunto de valores numéricos que
representan muestras de una señal, y queremos calcular la
transformada discreta de Fourier de estas muestras. La
transformada discreta de Fourier convierte el dominio del tiempo a
la frecuencia dominio, produciendo un conjunto de coeficientes
numéricos, para que podamos determinar la intensidad de varias
frecuencias en la señal muestreada. Además de estar en el centro
del procesamiento de señales, las transformadas discretas de
Fourier tienen aplicaciones en la compresión de datos y en la
multiplicación de polinomios y enteros grandes. El Capítulo 30 ofrece
un algoritmo eficiente, la transformación rápida de Fourier
(comúnmente llamada FFT), para este problema, y el capítulo
también esboza el diseño de un circuito de hardware para calcular la
FFT.

Estructuras de datos
Este libro también contiene varias estructuras de datos. Una
estructura de datos es una forma de almacenar y organizar datos
para facilitar el acceso y las modificaciones. Ninguna estructura de
datos única funciona bien para todos los propósitos, por lo que es
importante conocer las fortalezas y limitaciones de varios de ellos.

Técnica
Aunque puede usar este libro como un "libro de cocina" para
algoritmos, algún día puede encontrar un problema para el cual no
puede encontrar fácilmente un algoritmo publicado (muchos de los
ejercicios y problemas en este libro, por ejemplo). Este libro le
enseñará técnicas de diseño y análisis de algoritmos para que pueda
desarrollar algoritmos por su cuenta, demostrar que dan la
respuesta correcta y comprender su eficiencia. Los diferentes
capítulos abordan diferentes aspectos de la resolución algorítmica
de problemas. Algunos capítulos abordan problemas específicos,
como encontrar medianas y estadísticas de pedidos en el Capítulo 9,
calcular los árboles de expansión mínima en el Capítulo 23 y
determinar un flujo máximo en una red en el Capítulo 26. Otros
capítulos abordan técnicas, como dividir y conquistar en Capítulo 4,
programación dinámica en el Capítulo 15 y análisis amortizado en el
Capítulo 17.

Problemas difíciles
La mayor parte de este libro trata sobre algoritmos eficientes.
Nuestra medida habitual de eficiencia es la velocidad, es decir,
cuánto tiempo tarda un algoritmo en producir su resultado. Sin
embargo, hay algunos problemas para los cuales no se conoce una
solución eficiente. El capítulo 34 estudia un subconjunto interesante
de estos problemas, que se conocen como NP-completo.
¿Por qué son interesantes los problemas de NP completo? Primero,
aunque nunca se ha encontrado un algoritmo eficiente para un
problema NP-completo, nadie ha probado que no pueda existir un
algoritmo eficiente para uno. En otras palabras, nadie sabe si existen
o no algoritmos eficientes para problemas NP-completos. En
segundo lugar, el conjunto de problemas NP-completos tiene la
notable propiedad de que si existe un algoritmo eficiente para
cualquiera de ellos, entonces existen algoritmos eficientes para
todos ellos. Esta relación entre los problemas NP-completos hace
que la falta de soluciones eficientes sea aún más tentadora. En tercer
lugar, varios problemas de NP completo son similares, pero no
idénticos, a problemas para los que sí conocemos algoritmos
eficientes. Los informáticos están intrigados por cómo un pequeño
cambio en la declaración del problema puede causar un gran cambio
en la eficiencia del algoritmo más conocido.
Debe conocer los problemas de NP completo porque algunos surgen
sorprendentemente a menudo en aplicaciones reales. Si se le pide
que produzca un algoritmo eficiente para un problema de NP
completo, es probable que pase mucho tiempo en una búsqueda
infructuosa. Si puede demostrar que el problema es NP-completo,
puede dedicar su tiempo a desarrollar un algoritmo eficiente que
ofrezca una buena solución, pero no la mejor.

Como ejemplo concreto, considere una empresa de entrega con un


depósito central. Cada día, carga cada camión de entrega en el
depósito y lo envía para entregar productos a varias direcciones. Al
final del día, cada camión debe terminar de regreso en el depósito
para que esté listo para ser cargado para el día siguiente. Para
reducir costos, la compañía quiere para seleccionar un orden de
paradas de entrega que produzca la distancia total más baja
recorrida por cada camión. Este problema es el conocido "problema
del vendedor ambulante" y es NP-completo. No tiene un algoritmo
eficiente conocido. Sin embargo, bajo ciertas suposiciones,
conocemos algoritmos eficientes que brindan una distancia general
que no está muy por encima del mínimo posible. El capítulo 35 trata
sobre tales "algoritmos de aproximación".

Paralelismo
Durante muchos años, pudimos contar con que las velocidades del
reloj del procesador aumentaran a un ritmo constante. Sin embargo,
las limitaciones físicas presentan un obstáculo fundamental para las
velocidades de reloj cada vez mayores: debido a que la densidad de
potencia aumenta de manera superlineal con la velocidad del reloj,
los chips corren el riesgo de derretirse una vez que sus velocidades
de reloj se vuelven lo suficientemente altas. Para realizar más
cálculos por segundo, por lo tanto, los chips están siendo diseñados
para contienen no solo uno sino varios "núcleos" de procesamiento.
Podemos comparar estas computadoras multinúcleo con varias
computadoras secuenciales en un solo chip; en otras palabras, son
un tipo de "computadora paralela". Para obtener el mejor
rendimiento de las computadoras multinúcleo, necesitamos diseñar
algoritmos teniendo en cuenta el paralelismo. El Capítulo 27
presenta un modelo para algoritmos "multiproceso", que
aprovechan múltiples núcleos. Este modelo tiene ventajas desde un
punto de vista teórico, y forma la base de varios programas
informáticos exitosos, incluido un programa de ajedrez de
campeonato.

Ejercicios
1.1-1
Dé un ejemplo del mundo real que requiera clasificación o un
ejemplo del mundo real que requiera calcular un casco convexo.
1.1-2
Además de la velocidad, ¿qué otras medidas de eficiencia se podrían
usar en un entorno real?
1.1-3
Seleccione una estructura de datos que haya visto anteriormente y
analice sus fortalezas y limitaciones.
1.1-4
¿En qué se parecen los problemas de camino más corto y vendedor
ambulante que se mencionan anteriormente? ¿En qué se
diferencian?
1.1-5
Proponga un problema del mundo real en el que solo funcione la
mejor solución. Luego, encuentre una en la que una solución que sea
"aproximadamente" la mejor sea buena
suficiente.

1.2 Algoritmos como tecnología

Supongamos que las computadoras fueran infinitamente rápidas y la


memoria de la computadora estuviera libre. ¿Tendrías alguna razón
para estudiar algoritmos? La respuesta es sí, si no por otra razón que no
sea que todavía desea demostrar que su método de solución termina y
lo hace con la respuesta correcta.

Si las computadoras fueran infinitamente rápidas, cualquier método


correcto para resolver un problema funcionaría. Es probable que desee
que su implementación esté dentro de los límites de las buenas
prácticas de ingeniería de software (por ejemplo, su implementación
debe estar bien diseñada y documentada), pero a menudo utilizará el
método que sea más fácil de implementar.

Por supuesto, las computadoras pueden ser rápidas, pero no son


infinitamente rápidas. Y la memoria puede ser económica, pero no es
gratuita. El tiempo de computación es, por lo tanto, un recurso limitado,
y también lo es el espacio en la memoria. Debe usar estos recursos
sabiamente, y los algoritmos que son eficientes en términos de tiempo
o espacio lo ayudarán a hacerlo.

---------------------------------------------------------------------------------------

Das könnte Ihnen auch gefallen