Conceptos básicos: Algoritmos y aproximaciones

En el siguiente trabajo pretendemos presentar una serie de concepto y definiciones propios del estudio de los Algoritmos, su análisis y diseño. En el mismo podremos encontrar los conceptos de algoritmo y algunos de sus componentes, análisis y diseño. También veremos los diferentes tipos de formas y tamaños o medidas en que se pueden almacenar y representar los datos y estructuras en un algoritmo o programa. En ese mismo orden encontraremos las diferentes técnicas para diseñarlos como son el método de la fuerza bruta, el voraz, divide y vencerás, programación dinámica, de vuelta atrás, entre otros. De igual forma podremos ver las definiciones y algunas características, reglas, normas, tipos de algoritmos de búsqueda y ordenación así como sus aplicaciones. Finalmente veremos los que es la verificación y derivación de programas, donde daremos los conceptos básicos de semántica y sus tipos haciendo mayor énfasis en la semántica axiomática, la recursividad e iteración, los diseños de estos últimos, así como los típicos ciclos utilizados en algoritmos y programas y los paso a tener en cuenta al momento de desarrollar un algoritmo iterativo o recursivo. Es importante el estudio y conocimiento de lo que hoy conocemos como Algoritmos Computacionales, que desde su aparición hasta nuestros días es, y seguirá siendo; vital para el desarrollo de aplicaciones para computadoras y el manejo y dominio de la lógica de programación para resolver problemas. Como estudiantes de la Facultad de Ciencias y Tecnología " Escuela de Informática y Computación " de la Universidad Dominicana Organización y Métodos O&M con aspiraciones de iniciarnos como Ingeniero en Sistemas y Computación. Con el objetivo inmediato de aprobar con los mejores meritos la asignatura de Algoritmos Computacionales. General: Posibilitar la estudiante alcanzar una visión sistemática de lo que conocemos sobre Los Algoritmos Computacionales. Específicos : Introducir los conceptos propios sobre Algoritmo, su importancia en el mundo de las aplicaciones para computadoras y el manejo de lógica de programación.
y y y y y y

Proporcionar una idea de su uso. Visualizar sus ventajas e importancia. Definir sus tipos y variantes. Proporcionar conceptos sobre su análisis y diseño. Proporcionar concepto sobre las técnicas de diseño. Desglosar sus variantes (ordenación, búsqueda, etc. ).

Marco Historico. Un algoritmo es un conjunto de operaciones y procedimientos que deben seguirse para resolver un problema. La palabra algoritmo se deriva del nombre latinizado del gran Matemático Árabe Mohamed Ibn Al Kow Rizmi, el cual escribió sobre los años 800 y 825 su obra Quitad Al Mugabala, donde se recogía el sistema de numeración hindú y el concepto del cero. Fue Fibinacci, el que tradujo la obra al latín y el inicio con la palabra: Algoritmi Dicit. El lenguaje algorítmico es aquel por medio al cual se realiza un análisis previo del problema a resolver y encontrar un método que permita resolverlo. El conjunto de todas las operaciones a realizar y e orden en que se deben efectuarse, se le denomina algoritmo.

Es un método para resolver un problema mediante una serie de datos precisos, definidos y finitos. Generalidades El programador de computadoras es ante que nada una personaque resuelve problemas, por lo que para llegar a ser un programador eficaz se necesita aprender a resolver problemas de un modo riguroso y sistemático. A la metodología necesaria para resolver problemas mediante programas se denomina Metodología de la Programación. El eje central de esta metodología es el concepto, ya tratado, de algoritmo. Un algoritmo es un método para resolver un problema. Aunque la popularización del término ha llegado con el advenimiento de la era informática, algoritmo proviene de Mohammed alKhowarizmi, matemático persa que vivió durante el siglo IX y alcanzo gran reputación por el enunciado de las reglas para sumar, restar, multiplicar y dividir números decimales; la traducciónal latín del apellido de la palabra algorismus derivo posteriormente en algoritmo. Euclides, el gran matemático griego (del siglo IV antes de Cristo) que invento un método para encontrar el máximo común divisor de dos números, se considera con Al-Khowarizmi el otro gran padre de la algoritmia ( ciencia que trata de los algoritmos). El profesor Niklaus Wirth, inventor de Pascal, Modula-2 y Oberon, titulo uno de sus mas famosos libros, Algoritmos + Estructuras de Datos = Programas, significándonos que solo se puede llegar a realizar un buen programa con el diseño de un algoritmo y una correcta estructura de datos. Esta ecuación será de una de las hipótesis fundamentales consideradas en esta obra. La resolución de un problema exige el diseño de un algoritmo que resuelva el problema propuesto. Los pasos para la resolución de un problema son: 1. Diseño de algoritmo, que describe la secuencia ordenada de pasos que conducen a la solución de un problema dado. (Análisis del problema y desarrollo del algoritmo). 2. Expresar el algoritmo como un programa de lenguaje de programación adecuado. (Fase de codificación.) 3. Ejecución y validación del programa por la computadora. Para llegar a la realización de un programa es necesario el diseño previo de algoritmo, de modo que sin algoritmo no puede existir un programa. Los algoritmos son independientes tanto del lenguaje de programación en que se expresan como de la computadoraque lo ejecuta. En cada problema el algoritmo se puede expresar en un lenguaje diferente de programación y ejecutarse en una computadora distinta; sin embargo, el algoritmo será siempre el mismo. Así, por ejemplo, en una analogía con la vida diaria, una receta de un plato de cocina se puede expresar en español, ingles o francés, pero cualquiera que sea el lenguaje, los pasos para la elaboración del plato se realizaran sin importar el idioma del cocinero. En la cienciade la computación y en la programación, los algoritmos son más importantes que los lenguajes de programación o las computadoras. Un lenguaje de programación es tan solo un medio para expresar un algoritmo y una computadora es solo un procesador para ejecutarlo. Tanto el lenguaje de programación como la computadora son los mediospara obtener un fin: conseguir que el algoritmo se ejecute y se efectúe el proceso correspondiente. Dada la importancia del algoritmo en la ciencia de la computación, un aspecto muy importante será el diseño de algoritmos. El diseño de la mayoría de los algoritmos requiere creatividady

conocimientos profundos de la técnica de la programación. En esencia, la solución de un problema se puede expresar mediante un algoritmo. Características de los Algoritmos: Las características fundamentales que debe cumplir todo algoritmo son:
y y y

Un algoritmo debe ser preciso e indicar el orden de realización de cada paso. Un algoritmo debe estar definido. Si se sigue un algoritmo dos veces, se debe obtener el mismo resultado cada vez. Un algoritmo debe ser finito. Si se sigue un algoritmo se debe terminar en algún momento; o sea, debe tener un numero finito de pasos.

La definición de un algoritmo debe definir tres partes: Entrada, Proceso y Salida. En el algoritmo de receta de cocina citado anteriormente se tendrá: Entrada: ingrediente y utensilios empleados. Proceso: elaboración de la receta en la cocina. Salida: terminación del plato (por ejemplo, cordero). Ejemplo de Algoritmo: Un cliente ejecuta un pedido a una fábrica. Esta examina en su banco de datos la ficha del cliente; si el cliente es solvente entonces la empresa acepta el pedido; en caso contrario rechazara el pedido. Redactar el algoritmo correspondiente. Los pasos del algoritmo son: 1. 2. 3. 4. 5. inicio leer el pedido examinar la ficha del cliente si el cliente es solvente aceptar pedido; en caso contrario, rechazar pedido fin

Diseño del Algoritmo: En la etapa de análisis del proceso de programación se determina que hace el programa. En la etapa de diseño se determina como hace el programa la tarea solicitada. Los métodos mas eficaces para el proceso de diseño se basan en el conocido por Divide y Vencerás, es decir, la resolución de un problema complejo se realiza dividiendo el problema en sub problemas y a continuación dividir estos sub problemas en otros de nivel mas bajo, hasta que pueda ser implementada una solución en la computadora. Este método se conoce técnicamente como diseño descendente (Top Down) o modular. El proceso de romper el problema en cada etapa y expresar cada paso en forma más detallada se denomina refinamiento sucesivo. Cada sub programa es resuelto mediante un modulo (sub programa) que tiene un solo punto de entrada y un solo punto de salida. Cualquier programa bien diseñado consta de un programa principal (el modulo de nivel mas alto) que llama a sub programas (módulos de nivel mas bajo) que a su vez pueden llamar a otros sub programas. Los programas estructurados de esta forma se dice que tienen un diseño modular y el método de romper el programa en módulos más pequeño se llama Programación Modular. Los módulos pueden ser planeados, codificados, comprobados y depurados independientemente (incluso por diferentes programadores) y a continuación combinarlos entre si. El proceso implica la ejecución de los siguientes pasos hasta que el programa se termina:

y y y y

programar modulo. Comprobar el modulo. Si es necesario, depurar el modulo. Combinar el modulo con los módulos anteriores.

El proceso que convierte los resultados del análisis del problema en un diseño modular con refinamiento sucesivo que permitan una posterior traducción al lenguaje se denomina diseño de algoritmo. El diseño del algoritmo es independiente del lenguaje de programación en el que se vaya a codificar posteriormente. 4. Análisis De Algoritmos Recursos De Computadores Y Complejidad Algoritmo: Conjunto de reglas para resolver un problema. Su ejecución requiere unos recursos. Un algoritmo es mejor cuantos menos recursos consuma, su facilidad de programarlo, corto, fácil de entender, robusto, etc. Criterio empresarial: Maximizar la eficiencia. Eficiencia: Relación entre los recursos consumidos y los productos conseguidos. Recursos consumidos: Tiempo de ejecución. Memoria principal: Entradas/salidas a disco. Comunicaciones, procesadores, etc. Lo que se consigue: Resolver un problema de forma exacta, forma aproximada o algunos casos. Recursos consumidos: Ejemplo. ¿Cuántos recursos de tiempo y memoria consume el siguiente algoritmo sencillo? i:= 0 a[n+1]:= x repetir i:= i + 1 hasta a[i] = x Respuesta: Depende. ¿De qué depende? De lo que valga n y x, de lo que haya en a, de los tipos de datos, de la máquina... En general los recursos dependen de: Factores externos. El ordenador donde lo ejecutemos: 286, Pentium III, Cray,... El lenguaje de programación y el compilador usado. La implementación que haga el programador del algoritmo. En particular, de las estructuras de datos utilizadas. Tamaño de los datos de entrada. Ejemplo. Calcular la media de una matriz de NxM. Contenido de los datos de entrada. Mejor caso. El contenido favorece una rápida ejecución. Peor caso. La ejecución más lenta posible. Caso promedio. Media de todos los posibles contenidos.

si el algoritmo es poco eficiente. Orden de complejidad de f(n): O(f) . O(T): Orden de complejidad de T.. ¿Existe una cota inferior y superior del número de ejecuciones? ¿Se puede convertir en un FOR? El análisis de algoritmos también puede ser a posteriori: implementar el algoritmo y contar lo que tarda para distintas entradas. luego se diferencia en una constante con los anteriores.. T(N) = N+1.? Sabemos que cada ejecución lleva un tiempo constante.. Bucles FOR: Se pueden expresar como una sumatoria. T(N) = 2N + 4. para el conteo de instrucciones. Podemos comparar con otros algoritmos. con los límites del FOR. ¿Se puede predecir cuándo se cumplirán las condiciones? Llamadas a procedimientos: Calcular primero los procedimientos que no llaman a otros. Instrucciones ejecutadas por el algoritmo... pero ¿qué significa T(N)? Tiempo de ejecución en segundos. Operaciones de entrada salida: Otra unidad de tiempo. externos no aportan información sobre el algoritmo.. Conclusión: Estudiar la variación del tiempo y la memoria necesitada por un algoritmo respecto al tamaño de la entrada y a los posibles casos. Normalmente usaremos la notación T(N)=.2 s N= 7. IF y CASE: Estudiar lo que puede ocurrir. T(4)= 0.5 min ¿Qué conclusiones podemos extraer? Análisis a priori: Evitamos la implementación.Los factores externos no aportan información sobre el algoritmo. u omega de T. -. Mejor caso y peor caso según la condición.. ¿Tardarán todas lo mismo? Ejecuciones del bucle principal. o una constante diferente. Bucles WHILE y REPEAT: Estudiar lo que puede ocurrir. Programa "cifras. Notaciones asintóticas: Indican como crece T.): Una unidad de tiempo. T(7)= 10 s N= 8. Suponiendo que b y c son constantes.exe": N= 4. cuántas instrucciones. T(8)= 3. Q (T): Orden exacto de T. T(N) = bN + c. o alguna constante.. T(5)= 5 ms N= 6. Algunas reglas básicas. Ejemplo. de forma aproximada (y parametrizada). ¿Cuánto tiempo. Operaciones básicas (+. W (T): Orden inferior de T. *. Nos interesa un análisis que sea independiente de esos factores. con los segundos que tardan las operaciones básicas correspondientes.. Podemos hacer previsiones. :=. Medidas Asintoticas Notación asintótica: El tiempo de ejecución T(n) está dado en base a unas constantes que dependen de factores externos. para valores suficientemente grandes (asintóticamente) sin considerar constantes. T(6)= 0. Asignación de tiempos.1 ms N= 5.

se cumple: i) limn¥ ® f(n) Î R+ Þ O(f)=O(g).... Dadas f y g de N en R+. nm) suficientemente grandes. no sólo tiempos de ejec. "Funciones acotadas superiormente por un múltiplo de f. O(f)= { t: N ® R+ / $ c Î R+. Dadas f y g de N en R+.. l. W (f)=W (g). para valores de n suficientemente grandes.. Si f Î O(g) entonces O(f) Í O(g). de N en R+.. "Valores de n sufic.g) = O(max(f. llamamos orden de f al conjunto de todas las funciones de Nm en R+ acotadas superiormente por un múltiplo real positivo de f.xN ® R+) Ej. se cumple: i) limn¥ ® f(n) Î R+ Þ O(f) = O(g) g(n) ii) limn¥ ® f(n) = 0 Þ O(f) Ì O(g) g(n) iii) limn¥ ® f(n) = +¥ Þ O(f) É O(g) g(n) Notación con varios parámetros: En general.. -g))? P5. llamamos orden de f al conjunto de todas las funciones de N en R+ acotadas superiormente por un múltiplo real positivo de f. ¿Cómo es la relación para los W ? P3.. " n ³ n0: t(n) £ c·f(n) } Nota: O(f) es un conjunto de funciones. Propiedades P1. para valores de (n1. La definición es aplicable a cualquier función de N en R. . 2n+1 Î O(n)..": no nos importa lo que pase para valores pequeños. Q (f)=Q (g) g(n) ii) limn¥ ® f(n) = 0 Þ O(f) Í O(g). Ej. Si f Î W (g) y g Î W (h) entonces f Î W (h) Ej. n Î O(n2) Þ 2n+1 Î O(n2) P2. . g)).": nos quitamos las constantes. n2. O(f)=O(g) Û Q (f)=Q (g) Û f Î Q (g) Û W (f)=W (g) P7. M(B. ¿Qué relación hay entre O(log2 n) y O(log10 n)? P6. f: Nm ® R+ (f: Nx. O(f+g) = O(max(f. el tiempo y la memoria consumidos pueden depender de muchos parámetros. Dadas f y g de N en R+. W (g) Í W (f) g(n) P5. Memoria en una tabla hash. Dadas f y g.... Si f Î O(g) y g Î O(h) entonces f Î O(h). ¿se cumple O(f)Í O(g) ó O(g)Í O(f)? P4. se cumple: i) O(f) = O(g) Û f Î O(g) y g Î O(f) ii) O(f) Í O(g) Û f Î O(g) ¿La relación de orden entre O(. W (f+g) = W (max(f+g)) ¿Y para los Q (f+g)? ¿Es cierto que O(f ..) es completa? Dadas f y g..n. $ n0 Î N.Dada una función f: N ® R+. .m. nm): O(f) Dada una función f: Nm ® R+. k) = kB+l+n+2kn Orden de complejidad de f(n1. Grandes. no una función. Dadas f y g de N en R+.

siendo c y d constantes positivas. si p y q son polinomios del mismo grado. y del tiempo de inicialización b y de ejecución de un paso a. O(nm) O(n2).. t Î O(g) ‡Se cumple que: O(c) = O(d). O(c) Ì O(n) O(cn + b) = O(dn + e) O(p) = O(q). ±O(f) £ O(g) Û O(f) Í O(g) Û Para toda t Î O(f). si p es un polinomio de menor grado que q. tenemos W (f | P) y Q (f | P). $ n1. Orden exacto de f(n): Q (f): Dada una función f: N ® R+. llamamos orden de f según P (o condicionado a P) al conjunto: O(f | P)= { t: N ® R+ / $ c Î R+. llamamos omega de f al conjunto de todas las funciones de N en R+ acotadas inferiormente por un múltiplo real positivo de f. o variables T(N. ¿Qué relación hay entre los siguientes órdenes? O(n+m).. Ejemplo. encontrar la función f más simple tal que t Î O(f).. Podemos suponerlos constantes T(N). nm Î N. Orden inferior u omega de f(n): W (f): Dada una función f: N ® R+.. Ejemplo. para valores de n suficientemente grandes. " n ³ n0: P(n) Þ t(n) £ c·f(n) } De igual forma. t(n) = 2n2/5 + 3p /2. Para cualquier f y g. $ n0 Î N. asintóticamente y salvo constantes. O(p) Ì O(q). b) = a·N + b El tiempo depende del tamaño del problema N. Ejemplo. para funciones con varios parámetros. W (f)= { t: N ® R+ / $ c Î R+.. n2. O(n+2m) Notaciones condicionales: En algunos casos interesa estudiar el tiempo sólo para ciertos tamaños de entrada.a. $ n0 Î N.. a. km) £ c·f(k1. k2. llamamos orden exacto de f al conjunto de todas las funciones de N en R+ que crecen igual que f..O(f)= { t: Nm ® R+ / $ c Î R+. T(N) = T(N.) = Relación de inclusión entre conjuntos.. . ¿O(f) « O(f | P)? Ordenes De Complejidad Uso de los órdenes de complejidad: Dado un tiempo t(n). " n ³ n0: t(n) ³ c·f(n) } La notación omega se usa para establecer cotas inferiores del tiempo de ejecución. y P: N ® B. podemos extender los conceptos de W (f) y Q (f). km) } De la misma forma. . " k1 ³ n1 . ‡Relación de orden entre O(. .b). Algoritmo de búsqueda binaria: Si N es potencia de 2 el estudio se simplifica. . Relación de orden: igual que antes. y que más se aproxime asintóticamente. Las propiedades se siguen cumpliendo ® Demostrarlo. O(f) = O(f | true). k2. t(n) Î O(n2)..." km ³ nm : t(k1. Orden condicionado de f(n): O(f | P) Dada una función f: N ® R+. k2 ³ n2 .. f Î O(g | false)..

independientemente de la base... 5. Muchos problemas pueden resolverse buscando una solución fácil y directa pero.001.. aparecerá un orden logarítmico O(log2 n)..) Ì O(n2) Ì O(n3) Ì . å i = n(n+1)/2 Î O(n2).. Los logaritmos son del mismo orden.. a esquemas muy generales que pueden adaptarse a un problema particular al detallar las partes generales del esquema. llamamos o pequeña de f al conjunto de todas las funciones de N en R+ que crecen igual que f asintóticamente: o(f)= { t: N ® R+ / lim t(n)/f(n) = 1}n¥ ® Esta notación conserva las constantes multiplicativas para el término de mayor orden. Ì O(2n) Ì O(n!) Ì O(nn) ¿Qué pasa con las omegas? ¿Y con los órdenes exactos? El orden de un polinomio anxn+. å im Î O(nm+1) i=1 i=1 i=1 Si hacemos una operación para n. otros son bastante complejos. El acto de diseñar un algoritmo puede considerarse como una tarea que difícilmente podrá ser del todo automatizada. +a1n + a0 t(n) Î o(amnm) ¹ o(nm) ¿o(amnm) Í O(amnm)? ¿o(t) Í O(t)? Costa de complejidad con frecuencia Algunas relaciones entre órdenes frecuentes: O(1) Ì O(log n) Ì O(n) Ì O(n·log n) Ì O(n·(log n)2) Ì O(n1. puede ser muy directo. d Î R+. una tarea difícil. El esquema mas sencillo quizás sea el llamado divide y vencerás.. y a pesar de que resulta mas adecuado en bastantes casos utilizar alguno de estos esquemas que realizar un diseño desde cero. pero con un poco de análisis puede encontrarse algoritmos más eficientes.Es necesario en este momento mencionar algo sobre como hacerlo. se decir. t(n) = amnm + am-1nm-1 + . No obstante. Una forma de facilitar esta labor consiste en recurrir a técnicas conocidas de diseño de algoritmos. basado en la descomposición de un problema en . otra para n/2.. idear un algoritmo continua siendo una labor bastante creativa donde los conocimientos y la experiencia del propio diseñador tiene un papel fundamental. El diseño de un algoritmo que resuelva un problema es.Q (f) = O(f) Ç W (f) = { t: N ® R+ / $ c. en general.+a1x+a0 es O(xn).. algunos resultan inmediatos de resolver. " n ³ n0: c·f(n) ³ t(n) ³ d·f(n) } Notación o pequeña de f(n): o(f): Dada una función f: N ® R+. $ n0 Î N. Este método. a la vez bastante ineficiente.. La investigaciónen esta área ha permitido descubrir un conjunto de métodos o esquemas de diseño hacia los cuales puede orientarse la realización de muchos algoritmos. Todo problema algorítmico es un reto para su diseñador. . Técnica de diseño de algoritmos Diseño de Algoritmos: Hasta ahora se han realizado algunos comentarios respecto a la necesidad de diseñar algoritmos correctos y eficientes utilizando los elementos de un lenguaje de programación . n/4. Ejemplo.. nnn å 1 = n Î O(n). llamado de fuerza bruta.

esto no es malo. Este método de trabajo es practicable. que debe completarse con otros conocimientos y. Supongamos que disponemos de una especificación precisa. y quizás el mejor. solo puede tomarse tras considerar varias solucionesde otras etapas mas simples. Por ultimo. se produzca cierto resultado. Consideraciones generales Si el hábil programador dispone de un recetario de algoritmos de donde poder seleccionar el más adecuado para cada problema. Por ejemplos: Algunos algoritmos de búsqueda de un elemento en un vector. Una solución por fuerza bruta también puede resultar adecuada como primera aproximación a la solución final. y a métodos basados en transformaciones del dominio para encontrar una solución mas fácilmente a un problema en un dominio transformado. El mas entendido. hay problemas cuya solución no puede hallarse sino mediante un proceso de búsqueda. Otro algoritmo realizaba un búsqueda dicotomica o binaria. porque su desarrollo puede permitir profundizar más sobre el problema y conocer propiedades que sean utilizadas para obtener otra versión más eficiente. con complejidad . completa y consistente del problema a resolver y queremos obtener un algoritmo en el que. puesto que existe un número reducido de esquema y técnicas de diseño. podríamos utilizar un algoritmo general llamado algoritmo del museo británico. siendo dicha solución finalmente adaptada al dominio original. poco reflexionada. dad su ineficacia. dados uno datos de entrada valido. la solución es dinámica. tenemos una solución voraz. Uno de ellos realizaba una búsqueda secuencial con complejidad lineal sobre el tamaño del vector y podía usarse con cualquier vector. Aprender los principiosbásicos del diseño de algoritmos podemos preguntarnos por un método aceptable. no es un esquema algorítmico. a pesar de lo complejas que son las operaciones de búsqueda. conviene conocer otros métodos de diseño de algoritmos que también resultan de utilidad práctica. pero dado que no se ha analizado apenas el problema. es muy probable que no se hayan aprovechado propiedades deducibles del problema y que la solución sea terriblemente ineficiente. Método de fuerza bruta Comenzamos el estudio de esquemas algorítmicos con un método sencillo. Nos estamos refiriendo a métodos basados en la mejora de la eficiencia (por ejemplo. sobre todo. si la decisión en una etapa. y el empleode tablas como estructura auxiliar para la resolución eficiente de problemas donde se aplica programación dinámica). Otros esquemas requieren un análisis minucioso del problema de forma que la solución se vaya construyendo en etapas. su tarea se simplifica. con la experiencia. su uso adecuado mediante el esquema de búsqueda con retroceso (o backtracking) permite ganar gran eficiencia respecto a soluciones de fuerza bruta. Aun así. En realidad. Si no nos importa la eficiencia del algoritmo. es organizar el diseño sobre un esquema de algoritmo o una técnica de diseño que haya demostrado su utilidad para otros problemas. Se programa un computador de manera que parta de un conjunto de axioma matemáticos y los que use para reducir aleatoriamente teoremas validos. si no mas bien calificativo Para una forma de diseñar algoritmos: tomar una solución directa. la fuerza bruta. Si puede preverse que decisión conviene en cada etapa para producir cierto tipo de mejor resultado. En principio. el uso de parámetros de acumulación al resolver problemas utilizando divide y vencerás. El conocimiento de técnicas de diseño es solo un primer paso para el diseñador. pero que debe evitarse siempre que se pueda.subproblemas.

Otra técnica útil es el uso de tablas. Cada una se ilustra con un ejemplo distinto. se almacena en una tabla. pero no todos: hay algunos fácilmente formulables. El algoritmo primero responde a un razonamiento más sencillo. Lo más razonable es comprobar si el vector esta ordenado y. dichos algoritmos pueden servir como una primera aproximación al algoritmo definitivo. Tabulacion No todos los algoritmos recursivos ineficientes pueden optimizarse con la técnica de los parámetros acumuladores. Técnicas de los Parámetros Acumuladores y de Tabulacion La recurcion es un mecanismo que permite obtener. cuya idea básica se expone a continuación. Un modo de evitar problema lo proporciona la técnica de los parámetros acumuladores. y solo se podía usar cuando el vector estuviese ordenado.B. Parámetros Acumuladores Veamos primero una solución ineficiente que intentaremos mejorar. Veremos dos parámetros para la mejora de eficiencia de algoritmos recursivos: el uso de parámetros acumuladores y el uso de tablas. La función principal usa una función auxiliar que tiene los parámetros de aquellas más algunos adicionales. por lo que uno puede sentirse tentado a usar siempre. La función principal simplemente realiza una llamada a esta función auxiliar en los que los parámetros de aquellas se modifican y los parámetros nuevos toman un valor inicial adecuado . donde puede consultarse otras veces que se necesite. La intención es que la primera vez que se realiza un cálculo. pero muy ineficientes. en caso positivo. En estos casos. Muchos algoritmos recursivos resultan eficientes. la modificación para incorporar probabilidades diferentes es evidente y no complica el problema. en combinación con otras contrucciones. Ejemplo: Sea el problema de la competición. Esta técnica también se suele emplear con la programación dinámica. Por sencillez . Hay dos participantes (deportistas o equipos. que juegan una competición que es ganada por el primero que venza en n partidos. Los parámetros adicionales tienen como misión ir acumulando resultados principales durante el proceso recursivo. se supone que ambos participantes tienen cualidades y preparación similar . pero debe mejorar su rendimiento para que sea práctico. Divide y vencerás: Consiste en descomponer un problema en un subproblema.logarítmica. pero poco reflexionada. A. no importa que). De todas formas. Esta es la solución de fuerza bruta: una solución directa. siendo ( n ) mayor que( 0 ). De forma que cada uno tiene un 50% de posibilidades de ganar cada partido. aprovechar esta circunstancia para usar el algoritmo más eficiente: el de búsqueda binaria. una solución funcional a muchos problemas. Ejemplo: Números de Fibonacci Los números de fibonacci suele especificarse como: Fib(0)=1 Fib(1)1 Fib(n+2)=fib(n)+fib(n+1) Esta especificación de los números de fibonacci tienen una formulación recursiva inmediata en estilo funcional. resolver independientemente los .

la moneda de mayor valor ( es decir. si es posterior. El procedimiento se repite sucesivamente hasta encontrar la palabra o decidir que no aparece. la búsqueda en estructuras ordenadas. cierta medida. Corrección. También influyen haciendo que nuestro algoritmo resulten más fáciles de leer y entender para otras personas. estas normas de estilo se dirigen hacia aspectos como la forma de construir los nombres de variables o tipo de datos que aparezcan. Ejemplo. 1. Puede emplearse en problemas de optimización.. El modo de encolumnar las distintas partes de un algoritmo para facilitar su lectura y comprensión. 2. etc. Pude aparecer obvio. la ordenación de vectores. palabras claves. se va procedimiento paso a paso realizándose la mejor elección (usando una función objetivo que respeta un conjunto de restricciones ) de entre las posibles. se trata de dar como cambio la menor cantidad posible usando estos tipos de monedas. Estilo y calidad de los programas van fuertemente unidos. los factores que identifican la calidad en ellos . la tipografía seguida ala hora de escribir nombres de variables. Método voraz: Este método trata de producir tipo de mejor resultado a partir de conjunto de opciones candidatas . Suponiendo que se disponga de cantidad suficiente de ciertos tipos diferentes de monedas de curso legal. las siguientes respuestas reflejan. el algoritmo debe funcionar.subproblemas para luego combinar sus soluciones y obtener la solución del problema original. Ante la pregunta ¿Cuáles son las característica de un buen algoritmo?.. la planificación en el orden de la ejecución de unos programas en un computador. La estrategia voraz aplicada comienza devolviendo. . Si no ha encontrado y es anterior se procede a buscarla en la primera mitad.Para ello. se buscara en la segunda mitad. como el conocido de la mochila. Ello asegura que tanto algoritmos como programa resulten legibles y puedan modificarse fácilmente en caso de necesidad. Los criterios de estilo pueden reflejarse en un conjunto de normas de estilo de codificación. y la normas sobre como y donde deben de introducirse los comentarios. subprogramas. cuando se pueda. Consideraciones y Criterios para Diseñar Algoritmos Algunas consideraciones estilísticas pueden contribuir a mejor la calidadde los algoritmos (y programas ) mediante la reducción del numero de errores que aparecen al desarrollar los. Ejemplo.etc. mientras el valor de dicha moneda sea mayor o igual al cambio que resta por dar). Dar un cambioutilizando el menor número de monedas Considérese ahora el problema de la devolución del cambio al realizar una compra (por ejemplo. El proceso finaliza cuando se ha devuelto todo el cambio. continua aplicándose el mismo criterio para la segunda moneda mas valiosa. en la búsqueda de caminos mínimos sobre grafos. pero resulta difícil de asegurar en algoritmos complejos. Se abre el diccionario por la pagina centrar(quedando dividido en dos mitades) y se comprueba si la palabra aparece allí o si es léxico gráficamente anterior o posterior. Búsqueda de una palabra en un diccionario Como ejemplo sencillo de aplicación de esta estrategia puede considerarse la búsqueda de una palabra en un diccionariode acuerdo con el siguiente criterio. en una maquina expendedora de tabaco). Nunca se debe olvidar que la característica más simple e importante de un algoritmo es que funcione. Generalmente. y así sucesivamente. Esta técnica se puede aplicar con éxito a problemas como la multiplicación de matrices.etc.

analizando durante cada etapa que elemento conviene añadir a la solución parcial ya existente. Un algoritmo voraz sigue el esquema anterior. A menudo. puede llamarse candidato al elemento tratado en cada paso. . La única complicación es comprobar que se siguen satisfaciendo las restricciones del problema. Es más frecuente que el subconjunto de la solución se vaya formando paso a paso. el candidato se incorpora definitivamente. se habla de la memoria y del tiempo de ejecución . Por ejemplo. Según esta descripción. Algoritmos voraces Esquema voraz Hay muchos problemas en los que se pretende obtener un subconjunto de n elementos que satisfaga ciertas restricciones y que optimice alguna medida. Al contrario. Si el algoritmo voraz se ha diseñado correctamente. Normalmente. Esta característica hace que aunque el análisis del problema sea arduo. el conjunto de candidatos que forman la solución está vacío. eficiente. Otro ejemplo se da cuando. Inicialmente. Claridad. la solución voraz siempre resulte sencilla. pero con la fortuna de que cada vez que añade un elemento a la solución se tiene la certeza de haber realizado la mejor elección posible. A pesar de que con la reducción de los costes del hardware es posible diseñar computadores más rápidos y con más memoria.3. ésta es la función por optimizar. y de acuerdo con los puntos de vista anteriores. la calidad de un algoritmo tiene muchas facetas y todas ellas importantes. por tanto. sea el problema de encontrar un subconjunto de los arcos de un grafo. Se supone que un problema de esta clasetiene al menos una solución. no hay que desperdiciar estos recursos y tratar de desarrollar algoritmos más eficientes. la primera solución encontrada es óptima. encontrando de una sola vez la solución completa y óptima. En particular. En realidad. Puede haber varias soluciones optimas. éste es un proceso repetitivo sencillo que trata sucesivamente los diferentes elementos del problema. la dificultad principal al diseñar un algoritmo voraz reside en encontrar un criterio en encontrar un criterio de selección que garantice la optimalidad de la solución. el problema parte de: y Una función objetivo que da el valor de una solución. estos problemas no se intentan resolver "de golpe ". claro. el problema incluye restricciones adicionales que limitan el número posible de soluciones. Por tanto. lo ideal es que nuestro algoritmo resulte correcto. permite formar una solución del problema. se desecha el candidato. es decir. el algoritmo debe estar bien documentación. Ciertos detalles o algunas partes especiales de los mismos pueden olvidarse fácilmente o quedar oscura si no están adecuadamente comentadas. Por lo que se ha descrito del esquema voraz. Resumiendo. Obviamente. En cada paso se intenta añadir el mejor de los candidatos restantes a dicha solución parcial. 4. fiable y fácil de mantener. La documentación ayuda a comprender el funcionamiento de los algoritmos. en cuyo caso no importa cual se elija. si satisface las restricciones del problema y. Si este conjunto ampliado sigue siendo válido. el algoritmo no debe desaprovechar recursos. dados unos ficheros almacenados en una cinta de que el tiempo de recuperación de un fichero cualquiera sea el mínimo en promedio. La dificultad principal para resolver esta clase de problemas estriba en el análisis necesario para poder formular un algoritmo que halle la solución en varios pasos. si dicho conjunto no es válido. Eficiencia. La eficiencia de un algoritmo se mide por los recursos que este consume. Para facilitar la descripción de este proceso.

y Un conjunto de restricciones sobre el valor de los datos de entrada y sobre la solución final del problema.. Es fácil encontrar una solución si en cada etapa se genera el subcalendario correspondiente a un equipo. A su vez. Una función que determine si cierto conjunto de candidatos es válido. pero si la función de selección es la adecuada.. sino que se utiliza durante el análisis del problema y es determinante en la elección de la función de selección.n). la decisión. la tabla de competición se va completando por filas. el lector puede intentar encontrar una solución voraz del problema del calendario. si permite formar alguna solución del problema. . Podemos representar el esquema voraz de la siguiente forma funcional: FUNCTION Voraz ( candidatos: ( 1. nunca cambian de opinión: una vez que un candidato es aceptado o rechazado en la solución. utilizar el menor número de monedas.. De todas formas. se parte de un conjunto de tipos de monedas válidas. en este caso. solución) VorazAcumulador (candidatos. Para ello. Además.. Como ejercicio. de las que se supone que hay cantidad suficiente para realizar el desglose.n) -> FUNCTION VorazAcumulador ( candidatos : (1. Como fila primera se toma la secuencia de los índices de los participantes en cualquier orden. ( ) ) Puede verse por qué estos algoritmos se llaman " voraces " : en cada paso toman el mejor trozo de la solución. Desglose en monedas Como primer ejemplo introductorio sencillo al que puede aplicarse la técnica voraz. la solución consta de: y y y Un conjunto de candidatos Una función de selección que en cada momento determine que candidato de los aún no usados parece ser el mejor. cada solución válida y completa es optima. tales que sumados sus valores equivalgan al importe. Además. es decir. La función objetivo no suele aparecer en el algoritmo final. Solución : (1. se considera el problema de un cambio o desglose en monedas.n) : (1. debe recordarse que puede haber varios criterios alternativos de selección y que de su correcta elección depende que la solución calculada por el algoritmo sea optima.n) -> Cadidatos = ( ) v EsSolución ( solución)-> Value siguiente -> seleccionar ( candidatos ) IN EsVálida (solución v ( siguiente)) => VorazAcumulador (candidatos ± (solución). solución v (siguiente)) VorazAcumulador (candidatos ± (siguiente). Hay que desglosar una cantidad en un conjunto de monedas tratando de cumplir alguna condición.. este algoritmo tiene la ventaja de valer para las situaciones en que el número de participantes no es una potencia de dos.n ) : ( 1. es decir. es definitiva. Cada fila resultante puede tener una complejidad de o (n2). y de un importe. el mejor candidato. Se trata de indicar la cantidad (menor) de monedas de los tipos considerados. Obsérvese que las funciones de validez y completitud no se preocupan de la optimalidad del la solución. es decir.

La condición de factibilidad de la solución siendo construida establece en el desglose debe ser menor o igual que el importe a desglosar. 50. Después se resuelven estos subproblemas y se combinan las soluciones para obtener la solución para el problema original. cuando un candidato (moneda) se incorpora al conjunto solución. Este esquema de partición de problemas se denomina esquema de divide y vencerás solo en el caso en que los problemas sean de la misma clase del problema original. mientras sea posible. deben existir algunos pasos sencillos cuya solución pueda calcularse fácil y directamente.M1 Se supone inicialmente asignados los valores a cada uno de los tipos de monedas. Esquema de Divide y vencerás. Esta restricción permite una formulación y resolución recursiva de los subproblemas. 100. podemos utilizar sólo monedas de 500. Estos subproblemas se resuelven independientemente y después se combinan sus soluciones parciales para obtener la solución del problema original. Con esta información se puede comprobar que en este problema están presentes los distintos elementos de la técnica voraz. El caso más frecuente es cuando el número de subproblemas es dos. de tipo resultado: TYPEVAR     . La función objetivo cosiste en minimizar la cantidad total de monedas utilizadas en el desglose. La función de selección establece que hay que elegir. Su formación funcional es como sigue. suponemos que manejamos dineroespañol y. Una solución viene dad por un conjunto de monedas devuelto tras el desglose. el proceso recursivo nunca terminaría. Estos valores se definen por medio de un tipo enumerado MONEDAS. 1<k<=n. Asimismo. Además. Valores -> Integer M500 M1 Cantidades -> Integer M500 . La técnica de divide y vencerás es quizás una de las utilizadas debido a su sencillez: si un problema es demasiado grande para resolverlo de una vez. 5 y 1 pesetas para el desglose. y cuyo valor total es igual al importe a desglosar. Veamos el esquema de divide y vencerás para dos subproblemas. la técnica de divide y vencerás parte la entrada en k subproblemas. Los elementos de la técnica voraz están presentes en este problema de la siguiente forma: y y y y y El conjunto de candidatos está constituido por cada una de las monedas de los diferentes tipos que se pueden usar para realizar el desglose del importe dado. se descompone en varias partes más fáciles de resolver. en particular. se declaran los tipos VALORES y CANTIDADES para representar el valor asignado a cada unidad monetaria y la cantidad de cada tipo de moneda que se devolverá en el desglose. dado un problema al resolver planteando en términos de una entrada de tamaño n. es fácil su generalización a k subproblemas 2<k<=n. considerado el problema como de tipo dato y la solución. 25. en caso contrario. éste no será nunca excluido de él. Mas formalmente. Por supuesto. la moneda de mayor valor de entre las candidatas.Para simplificar. Divide Y Vencerás La técnica divide y vencerás consiste en descomponer el problema en un conjunto de subproblemas más pequeños. Su declaración es la siguiente: TYPE Monedas -> M500 I M100 I M50 I M25 I M5 I M1.

N. inferior. Elaboración de un Calendario Deportivo: Sea un campeonato deportivo. IN inferior. Por concreción. 1. La eficiencia final del algoritmo depende de la función f(n) concreta que aparezca durante el análisis.n. inferior. OUT solución : resultado) -> VAR medio: 1. superior. para que esta técnica resulte eficiente todos los subproblemas deben ser de tamaño parecido. solución) DyVAux (problema. subsolucion2). Si el tamaño de los dos subproblemas es el mismo (o casi).. superior) THEN ResolverDirectamente (problema. subsolucion1). en la que se utiliza un vector de tamaño N. olución) ELSE Medio := Partir (inferior.N. resultado PROCEDURE DivideYVenceras (IN problema : dato1. para nuestros propósitos resulta indiferente el deporteobjeto de la competición. medio+1. Combinar (subsolucion1. Partir y Combinar por funciones o procedimientos concretos. así que hablaremos de participantes en vez de deportistas o equipos. resultado FUNCTION DivideYVenceras (problema : dato) : resultado -> EsPequeño (problema) }=> ResolverDirectamente (problema) | VALUE subproblemas -> Partir (problema) IN subproblemas == (subproblema1. Sin embargo..N subsolucion1. DivideYVenceras (subproblema2)) Se puede hacer una formulación imperativa similar. superior : 1. OUT solución : resultado) -> PROCEDURE DyVAux (IN problema : dato1.n.Dato. solución) El esquema general se adapta a un problema concreto al sustituir los metasimbolos EsPequeño. Nótese que. superior). subsolucion2. el tiempo de cómputo de la función DivideYVecneras se describe con la siguiente relación de recurrencia: g(n). TYPEVAR dato.. subsolucion2 : resultado IF EsPequeño (inferior. El problema consiste en elaborar un calendario de competición de forma que cada participante compita exactamente una vez con cada uno de los demás participantes. puede suponerse que las competiciones se celebran en días sucesivos y . y sin perdida de generalidad.. DyVAux (problema. g(n) es el tiempo que tarda la función ResolverDirectamente en resolver problemas de pequeño tamaño (normalmente una constante) y f(n) es el tiempo necesario para partir el problema y combinar las subsoluciones. es general.si n es pequeño T(n) = 2 T(n/2) + f(n). escribiremos una formulación más restrictiva pero bastante usual. medio. subproblema2) => Combinar (DivideYVenceras (subproblema1) . en caso contrario donde T(n) es la función de tiempo de DivideYVenceras para entradas de tamaño n. DyVAux (problema. superior. ResolverDirectamente.

Se dispone de una solución inmediata aplicando fuerza bruta. A su vez.n}-{i} ahora se completan las filas de la tabla de todas las formas posibles. la solución del problema puede representarse en una tabla de dimensión nx(n-1). incluyendo en cada fila i algún ejemplo de P(i). 1<=i<=n. se supone que el numero de participantes es una potencia de dos. hay n = 2k participantes para algún entero positivo k. es decir.. Por tanto. La siguiente figura describe visualmente parte de la elaboración de la tabla. El elemento (i. Cada conjunto P(i) consta de (n-1)! Elementos. pero es terriblemente ineficiente. el conjunto P(i) de todas las permutaciones posibles del resto de los participantes con los que debe competir. es decir. el conjunto de permutaciones de los números {1. porque el día j-esimo cada participante solo puede competir con otro participante. Para simplificar el problema. Se necesitan elaborar n-1 competiciones por participantes. Solo sirve como solución aquellas combinaciones de fila que cumplan las restricciones enunciadas en el párrafoanterior sobre las columnas de la tabla (las restricciones sobre las filas están garantizadas por el modo de generar los conjuntos P(i)). Primero se obtiene para cada participante i. días 1 participantes 1 2 2 1 1 2 3 1 2 3 4 2 1 4 3 3 4 1 2 4 3 2 1 1 2 3 4 5 6 7 1 2 3 4 5 6 7 8 2 1 4 3 8 5 6 7 3 4 1 2 7 8 5 6 4 3 2 1 6 7 8 5 5 6 7 8 1 2 3 4 6 5 8 7 4 1 2 3 7 8 5 6 3 4 1 2 . 1<=j<n. contiene el numero del participante contra el que el participante i-esimo compite el día j-esimo. se elige uno cualquiera.que cada participante compite una vez por día. la columna j también contiene números distintos. El método de fuerza bruta resulta sencillo. Si hay varios calendarios validos. 1<= i<=n. Se supone también que cada participante tiene asignado un número comprendido entre 1 y N. Obsérvese que los números de participantes incluidos en la fila i de la tabla son distintos porque el participante i-esimo solo debe competir una vez con cada participante restante. resultan nx(n-1)!=n! formas de rellenar la tabla.j)±esimo de la tabla. Dado que el numero de participantes de n. Sin embargo la aplicación de la técnica de divide y vencerás produce una solución mas sencillas aun pero muy eficientes.

la unión de estos subcalendarios no forma un calendario completo para el campeonato de 2k participantes. El algoritmo descrito se expresa a continuación. Después se genera.. sup.N.1 := inf ELSE medio := (inf + sup) Div 2. PROCEDURE Calendario ( INOUT tabla : (1. Por fortuna. medio. sup-1. es más complejo.sup-1. El siguiente participante toma esta secuencia y realiza una fácil permutación de la misma que le garantiza el respeto de las restricciones de la solución.. la mitad izquierda de la tabla. también de orden de complejidad cuadrática. tabla) Este sistema de ecuacionesdefina una función de tiempo del orden de O(n2). IN sup :1. que almacena los índices de las filas. El caso básico se da cuando solo hay dos participantes.N-1) -> VAR medio : 1. tabla).N..1 : = sup. tabla).N IF inf = sup-1 THEN tablainf. Finalmente se completa la mitad derecha de la tabla (correspondiente al cruce de los dos ¡ . CompletarTabla (medio+1. tabla). Si el numero de participantes es 2k . sucesivamente con los participantes 2k-1 +1.8 7 6 5 2 3 4 1 Se distinguen dos casos. es decir. FormarTabla (medio+1. OUT tabla : (1.. medio. mediante divide y vencerás. La solución es directa porque se celebra una sola competición entre ambos. de numeración comprendida entre 1 y 2k-1 y otro para los participantes comprendidos entre 2k-1 +1 y 2k . El calendario de los participantes de numeración superior se completa de forma similar con los números de los participantes de numeración inferior. En efecto. FormarTabla (inf. superior en orden creciente de numeración. Veamos otra estrategia. cuando hay más de dos participantes. faltando 2k x2k-1 celdas para completar el calendario total. rotando dicha secuencia a la derecha.N.. El caso recursivo.N)1. El problema puede reducirse a dos sub problemas de tamaño 2k-1 si se elaboran independientemente dos subcalendarios de tamaño 2k x(2k-1 -1): uno para los participantes.. puede decirse que el "tamaño" del problema es 2k (sabemos que el calendario tendrá un tamaño de 2k x(2k-1 -1) posiciones).N) 1.. medio.N-1) -> PROCEDURE FormaTabla (IN inf : 1.N. sup. tablasup. CompletarTabla (inf. donde se aplica divide y vencerás para resolver el problema y que se aprovecha de la simetría de la solución.1. Este proceso se repite para el resto de los participantes de numeración inferior. por ejemplo.. inf. ya que a unión de los dos calendarios tiene un tamaño 2k x(2k-1 -1). medio+1. Sin embargo.. que es mucho mas eficiente que la solución de fuerza bruta. El subcalendario del primer participante es sencillo porque basta con que compita en días sucesivos con los participantes de numeración. faltan por elaborar las competiciones cruzadas entre los participantes de numeración inferior y los de numeración superior.1. medio.. el resto del calendario se puede construir fácilmente.2n . para k>1. La idea consiste en añadir inicialmente a la tabla una columna "ficticia" de índice j=0. Completemos primero la parte de los participantes de numeración inferior. .

Ordenación de un Vector por Mezcla: La ordenación de un vector es un problema que se presta fácilmente a la aplicación de la técnica de divide y vencerás. es decir.N. IN medio: INTEGER. los valores de las casillas (k. IN sup : INTEGER. de acuerdo con las siguientes expresiones de los índices: i = (k + n/2) Mod (n+1) j = (1 + n/2) Mod n De esta forma se rellenan las casillas aun vacías. 1. índice : INTEGER i1 := inf... sup) OrdenarAux (v.1.l ya completadas. WHILE (i1<=medio) ^ (i2<=sup) DO IF vectori1 << vectori2 THEN vectorAuxj :=vectori1. i2 := medio + 1. El algoritmo resultante es: PROCEDURE Ordenar (INOUT v : INTEGER1.N IF inf < sup THEN medio := (inf+sup) Div 2. siendo 1<=k<=n y 0<=l<=(n/2)-1. IN inf. medio+1. El caso básico corresponde a un subvector de un solo elemento. la combinación de los dos subvectores ya ordenados es fácil. j := inf.s un vector de índice inferior i e índice superior s. N) El procedimiento para realizar la mezcla de los subvectores ordenados es: PROCEDURE Mezclar ( IN inf : INTEGER. En esta última etapa.= vectori2.s . los componentes tablai. basta con mezclar los dos subvectores. La partición puede hacerse por la mitad si se toma un índice m=[(i+s)/2] y dos subvectores vi..N. inf.N) -> (* ordenación por mezcla *) PROCEDURE OrdenarAux (INOUT Vector : INTEGER1. sea vi..N) -> VAR Medio : 1. sup). i2 := i2 + 1 . j : INTEGER.j a partir de las casillas tablak. i2.N.l).. que obviamente ya esta ordenado. Mezclar (vector.N) -> VAR vectorAux : INTEGER1. INOUT vector : INTEGER1. OrdenarAux (vector.. Para el caso general. i1... medio).. sup : 1. para obtener un único vector ordenado.grupos de equipos cuyos subcalendarios se han generado por divide y vencerás). OrdenarAux (vector. medio. Este proceso de mezcla es realizado por un procedimiento auxiliar. mediante comparaciones de sus elementos sucesivos.. i1 :=i1 + 1 ELSE vectorAuxj . inf.m y vm+1.

resultando: T(n) = 2T(n/2) + bn= =2K T(n/2K) + kbn = an + bn log2 n El algoritmo de ordenación por mezcla es óptimo en tiempo de ejecución. Multiplicación de Matrices: Sean dos matrices. es decir. b=cte Si n es una potencia de 2. de forma que las ecuaciones de recurrencia de la función de tiempo son: T(n) = a. a=cte 2T(n/2) + bn. necesita copiar el vector auxiliar completo en el principal. La matriz productoC=AxB también es una matriz de nxn cuyo elemento (i. Los únicos inconvenientes que presenta es que el procedimiento de mezcla necesita gran capacidad de almacenamiento (para dos copias del vector) y que. n>1.. así que el tiempo total del algoritmo de multiplicación es de orden O(n3). las ecuaciones anteriores se resuelven por sustituciones sucesivas. por sencillez.) las submatrices A y B pueden partirse en cuatro submatrices de dimensión (n/2)x(n/2). A y B. La matriz C tiene n2 elementos.. n=1. es decir. Puede diseñarse un algoritmo de mezcla más complejo que mejore ambos aspectos. Si el producto AxB tiene la forma: A11 A12 B11 B12 C11 C12 A21 A22 B21 B22 C21 C22 Entonces: C11 = A11*B11 + A12*B21 C12 = A11*B12 + A12*B22 C21 = A21*B11 + A22*B21 C22 = A21*B12 + A22*B22 ¢ .sup DO vectorindice := vectorAuxindice El algoritmo resultante es sencillo conceptualmente.sup DO vectorAuxj := vectorindice . (Si n no es un potencia de dos.j := j + FOR índice IN i1. J := j + 1 FOR índice In inf. pueden añadirse las filas y columnas de ceros necesarias para formar una dimensión que sea potencia de dos. El algoritmo anterior. que existe un entero no negativo k tal que n=2k. J := j + 1 FOR índice IN i2. de dimensión nxn.medio DO vectorAuxj := vectorindice.j)-esimo se forma multiplicando cada elemento de la final i-esima de A por el elemento correspondiente de la columna j-esima de B y sumando los productos parciales. que n es una potencia de dos. proviene directamente de la definición matemática del producto de matrices. La operación de mezcla es proporcional a n. pero mantenga la complejidad asintótica calculada. además de mezclar. Es fácil analizar la complejidad del algoritmo para un vector de longitud n. Sin embargo. Supongamos. que podemos llamar algoritmo convencional de multiplicación de matrices. El cálculo de cada elemento Cij requiere n multiplicaciones. la técnica de divide y vencerás sugiere un algoritmo distinto. n =2k para algún k..

En la programación dinámica todos los subproblemas se resuelven de acuerdo con criterio de tamaño creciente y los resultados de subproblemas más pequeños se almacenan en algún tipo de estructura de datos (normalmente tablas) para facilitar la solución de los problemas más grandes.Para n=2. todo problema resoluble con esta técnica debe de satisfacer el principio de optimalidad. Eli el estado del problema tras la elección del valor vli 1<i<n1 y Sli una secuencia óptima de decisiones respecto al estao Eli. Este principio establece que "una secuencia óptima de decisiones que resuelve un problema debe cumplir la propiedad de que cualquier subsecuencia de decisiones también debe ser óptima respecto al subproblema que resuelva ". conduciendo de forma directa a la solución. Sin embargo. resultará un total de d secuencias posibles de decisión. no se reconsidera en el futuro. asegurando que la secuencia de decisiones es la mejor de las posibles. La programación dinámica (también llamada planificación dinámica) es una técnica de programación que también permite resolver problemas mediante una secuencia de decisiones. La existencia de un algoritmo eficiente para la multiplicación (en realidad. una secuencia óptima de decisiones respecto a E0 es la mejor secuencias de decisión { Vli Sli }. La resolución de este sistema de ecuaciones nos dice que O(T(n))=OT(n3). Podría conseguirse mas eficiencia si lográramos realizar menos multiplicaciones de matrices. Sea D = { v1 . 1<i<n. el número de secuencias de decisión es exponencial sobre el número de decisiones. Dos submatrices de (n/2)x(n/2) pueden sumarse en un tiempo bn2. para cualquier operación de las anteriores) significaría la existencia de un algoritmo similar para las demás. El método es eficiente porque una vez que se toma una decisión en un paso.vn} el conjunto de valores de decisión posibles para la decisión d1. siendo b alguna constante. evitándose una explosión combinatoria en la producción de las secuencias y consiguiéndose soluciones más eficientes en cuanto a tiempo de ejecución. porque si hay d opciones para cada una de las n decisiones. asimismo. £ . Solamente al final se sabe cuál es la mejor de todas. Podemos formalizar algo más la idea básica. El algoritmo de Strassen calcula las cuatro submatrices Cij empleando 7 multiplicaciones y 18 sumas o restas de matrices. pero de una manera menos directa que en el caso voraz. aunque fuera a costa de un mayor numero de sumas de matrices. una característica es que el programa "aprende "dinámicamente de las decisiones que toma. como inversión de una matriz o hallar su determinante. Usando una técnica de fuerza bruta. los elementos Cij se calculan mediante algunas multiplicaciones y sumas de números.. Esta vez se necesita producir varias secuencias de decisiones. de forma que no se ha conseguido ningún ahorro sustancial de tiempo. pero para n>2 las submatrices Cij se calculan mediante multiplicaciones (recursivas) y sumas de submatrices de dimensión (n/2)x(n/2). interesa encontrar algoritmos mas eficientes. Entonces. dado que la complejidad respectiva de estas operaciones es O(n3)n y o(n2). tal que Eo es el estado inicial del problema y deben tomarse n decisiones d. Supongamos que tenemos un problema que satisface el principio de optimalidad. Programación Dinámica Principios de programación dinámica Se ha visto que la técnica voraz se aplica a problemas cuya solución puede formularse como el resultado de una secuencia de decisiones. 1<i<N1. porque la multiplicación esta relacionada con otras operaciones sobre matrices mas usuales. Además. No es fácil establecer una definición de la programación dinámica. no todos los problemas pueden resolverse de esta manera. Sin embargo. De esta forma se reduce al número total de subsecuencias generadas. sea.

La formulación delantera expresa la decisión de Xl . INOUT solucion : elemento1.xi+1) termina en un nodo de respuesta.. Esquema de Algoritmos de Vuelta Atrás: Sea (x1.1 ) debe expresarse en términos de los valores de decisión existente para decisiones d1 y el subproblema problema ( k+1. En algunos problemas de optimización se conoce un criterio óptimo de selección que puede usarse de forma voraz.n son aquellos valores generados por G que satisfacen A. a partir de la secuencia de decisiones Xi+1 Xn ( es la clase de formulación adoptada hasta ahora ). a partir de la recurrentes con formulación trasera es igual que e la formulación delantera. El Algoritmo de Vuelta Atrás se especifica de la forma siguiente: PROCEDURE Retroceso (IN k : INTEGER. Sin embargo... 1<i<n..xi+1) es falso si el camino (xi. entonces el problema completo es problema ( l. 1<i<n.. Supongamos que también existe algún predicado R que determina si un camino (x1. ( Obsérvese que vamos a usar la técnica de resolución de problemas por generalización para después poder realizar una particularización de la solución obtenida. todavía hay otros problemas peores que no queda mas remedio que realizar una búsqueda de la solución.xi) el camino desde la raíz hasta un nodo de un árbol del espacio de estado..xi) el conjunto de todos los valores posibles de xi+1 tales que (x1.dl. Por lo tanto..) Una solución dinámica para problema ( k.1 ) resultante de aplicar cada valor de decisión. la aplicación de la técnica de programación dinámica a un problema significa comprobar primero el principio de optimalidad y desarrollar después unas ecuaciones recurrentes del estilo de (1) y (2). Supongamos que existe algún predicado acotador A tal que A(x1. tiene la ventaja ( quizás paradójica al tratar de un problema más pequeño ) de que proporciona una visión más general del problema en cuestión. Sea X1 .. partiendo como estado inicial de Ek-1.. sencillamente. a tomar. Sea G(x1. Además. debe existir una función de criterios que debe ser satisfecha por cada secuencia solución u optimizada por dichas secuencias solución si solo queremos la mejor. 1<i<n . la ecuación de base establece el valor para la etapa n+1 en que no queda ninguna decisión Xi.n) -> ¤ ¤¤ ¤ . los candidatos para la posición i+1 del vector desolucion x1. En resumen... La expresión inicial de la ecuación de recurrencia. Tiene sentido centrarse en un subproblema del problema inicial porque éste satisface el principio de optimalidad pero..xi+1) es un camino hasta el estado del problema.n ). sólo que en orden contrario. La ecuación general relaciona la secuencia óptima en una etapa i con la decisión tomada en la etapa i y la subsecuencia óptima en la etapa posterior i+1. del gusto del programador.Xn la secuencia de decisiones necesaria para resolver el problema... Otros problemas satisfacen el principio de optimalidad..... puede generalizarse la formulación del problema a cualquier subsecuencia de decisiones dk .n ). Algoritmos De Vuelta Atrás Existen un alto número de problemas que pueden formularse como la búsqueda de la mejor solución o del conjunto de todas las soluciones que satisfacen ciertas condiciones. La formulación trasera expresa la decisión de Xi... La elección de una formulación delantera o trasera depende del problema considerado o. 1<k<n.... si este subproblema de simboliza como problema (k. Por supuesto.l).El razonamiento anterior se refiere a la primera decisión d1 tomada desde el estado inicial E0 sin embargo... cada solución es el resultado de una secuencia de decisiones.xi+1) no puede extenderse para alcanzar un nodo de respuesta. hay un caso en que la decisión d1 no va seguida por ninguna secuencia de decisiones.. La ecuación de recurrencia puede formularse de dos formas: delantera o trasera.. además. pudiéndose aplicar la técnica de programación dinámica. que es problema ( n..

Problema de optimización. donde la solución está formada por un grupo de elementos en cierto orden: podemos aplicar el esquema voraz. Algoritmos Heuristicos Existen muchos problemas para los cuales no se conocen algoritmos que puedan encontrar la solución de forma eficiente: problemas NP-completos. evitando así la exploración de gran parte de al estructura. Este mismo proceso se repite en el resto de nodos del árbol. Se sale del bucle FOR cuando no quedan mas valores para solución terminando la llamada actual al algoritmo. 1. IF R(solucion. La solución exacta puede requerir un orden factorial o exponencial: el problema de la explosión combinatoria. Posibilidades: . A). 1. En este punto podemos retroceder (y no seguir avanzando por mas ramas).VAR nodo : elemento FOR noso IN G(solucion.k) THEN << guardar µsolucion¶ >>. La estructura de algoritmo voraz se puede utilizar para construir procedimientos heurísticos: hablamos de heurísticas voraces. k sirve de cota inferior al retroceso. se comprueba si se ha encontrado una solucion. Ramificación (Bifurcacion) Y Acotación Los métodos de Ramificación y Acotación constituyen un a variante de las técnicas de retroceso para problemas donde se trata de encontrar el valor máximo o mínimo de cierta función objeto (esto suele suceder en los problemas de programación lineal entera). se basa en un conocimiento intuitivo del programador sobre un determinado problema. solucion). y que al seguir avanzando en el árbol (mediante la aplicación de varios pasos de retrocesos) se alcanza un nodo que requiere k+1 colores. encontrar un ciclo simple de costo mínimo que pase por todos los nodos. pero necesitamos una solución eficiente. El problema del viajante Problema: Dado un grafo no dirigido. 1. k) THEN IF R(solucion. La técnica de ramificación y acotacotacion aplica de la siguiente manera: Supóngase que al recorrer un árbol y alcanza una hoja se tiene una solucion con k colores. Es un problema NP. Objetivo: obtener buenas soluciones en un tiempo de ejecución corto. Así. completo y ponderado G = (V. Normalmente. pues tenemos ya una solucion mayor. k-1) DO Solucion k := nodo. Se hace necesario utilizar algoritmos heurísticos: Un algoritmo heurístico (o simplemente heurística) puede producir una buena solución (puede que la óptima) pero también puede que no produzca ninguna solución o dar una solución no muy buena. Después simplemente se llama recursivamente al algoritmo para generar los estados descendientes. Retroceso (k+1. El procedimiento no hace ninguna llamada recursiva cuando k = N+1 o cuando ningún nodo generado por G satisface el elemento posible que satisfacen A se añade una solución particular. solucion) La llamada inicial del algoritmo es Retroceso(1.

Selección: seleccionar la arista candidata de menor coste. ‡Ejemplo. (3. 3. . Sin embargo. c2.. pero garantizando que se forme un ciclo. ca). cn). el orden de visita de los nodos. 5)) Coste = 10+15+20+45+50 = 140 Conclusiones: Ninguno de los dos algoritmos garantiza una solución óptima. Empezando en el nodo 1. Para este tipo de problemas. . próximas a la óptima. Factible: una arista se puede añadir a la solución actual si no se forma un ciclo (excepto para la última arista añadida) y si los nodos unidos no tienen grado mayor que 2. 5). Hacer igual que en el algoritmo de Kruskal. Las aristas son los candidatos. los algoritmos que no conducen a una solución óptima se llaman algoritmos de aproximación. 4). (1. Se trata de calcular un subconjunto A¶ de aristas tal que dos aristas . es probable que no sepamos resolverlo de manera precisa y completa utilizando un algoritmo polimico en tiempo. 4. Posibles mejoras: buscar heurísticas mejores. 2. Ejemplo. 2) Coste: 30+15+25+10+45=125 Empezando en el nodo 3. a2. . Solución: ((2. Empezar en un nodo cualquiera. 2).1. En cada paso moverse al nodo no visitado más próximo al último nodo seleccionado. resulta parcialmente interesante que estos garanticen una cota en el margen de imprecisión.A).. Los nodos son los candidatos. repetir la heurística 1 con varios orígenes.. Inicialización: seleccionar un nodo cualquiera. 4. Acabamos cuando tengamos n nodos. 2.. Función de selección: de los nodos candidatos seleccionar el más próximo al último (o al primero) de la secuencia actual (c1. Solución: (5. Heurística voraz 1 ± Una solución será un cierto orden en el conjunto de nodos (c1.. (4. an-1) que formen un ciclo hamiltoniano.. 3. Este problema se puede resolver a través de otro aproximado. (1. se trata de encontrar un conjunto con el menor numero de vértices tal que toda arista sea incidente por lo menos de un vértice de V. A continuación se ilustra este tipo de tratamiento de problemas al problema de recubrimiento de un grafico: Dado un grafo G=(V. 3). Empezar con un grafo sin aristas.. 5. Algoritmos De Aproximación Dado un problema NP completo.. 1) Coste: 15+20+10+45+50=140 Heurística voraz 2 ± Una solución será un conjunto de aristas (a1. normalmente ambos dan soluciones buenas.. ó bien. c2. a partir de la solución del algoritmo intentar hacer modificaciones locales para mejorar esa solución. Sin embargo. como es calcular el ajuste maximizal del grafo G. sin importar el orden. Solución: (1.

el voraz. En el mismo podremos encontrar los conceptos de algoritmo y algunos de sus componentes. El procedimiento para construir un ajuste maximizal de un grafo G consistiría en ir tomando aristas de G. divide y vencerás. Este nuevo problema garantiza conseguir un recubrimiento que contiene no más de dos vértices del recubrimiento mínimo. En consecuencia. También veremos los diferentes tipos de formas y tamaños o medidas en que se pueden almacenar y representar los datos y estructuras en un algoritmo o programa. ningún vértice perteneciente a M puede recubrir a mas de una arista en M. los diseños de estos últimos. que desde su aparición hasta nuestros días es. así como los típicos ciclos utilizados en algoritmos y programas y los paso a tener en cuenta al momento de desarrollar un algoritmo iterativo o recursivo. Finalmente veremos los que es la verificación y derivación de programas.análisis y diseño. de una en una y en cualquier orden e ir eliminando las incidentes al conjunto que se esta construyendo hasta recubrir todo en grafo. reglas. también por la propia definición. la recursividad e iteración. seria necesario demostrar que el conjunto de todos los vértices inciden a las aristas de un ajuste maximal M para un grafo G es un recubrimiento con no mas de dos veces el numero de veces el recubrimiento de tamaño mínimo. por lo menos la mitad de los vértices de M deben pertenecer a un recubrimiento. entre otros. de vuelta atrás. vital para el desarrollo de aplicaciones para computadorasy el manejo y dominio de la lógica de programación para resolver problemas. y seguirá siendo. Con el objetivoinmediato de aprobar con los mejores meritos la asignatura de Algoritmos Computacionales. Justificacion Es importante el estudio y conocimiento de lo que hoy conocemos como Algoritmos Computacionales. programación dinámica.cualquiera de A¶ no tengan ningún vértice común y toda arista de A-A¶ comparta algún vértice común con una arista de A¶. su análisis y diseño. Objetivos General : Posibilitar la estudiante alcanzar una visión sistemática de lo que conocemos sobre Los Algoritmos Computacionales. Motivación Como estudiantes de la Facultad de Ciencias y Tecnología " Escuela de Informática y Computación " de la Universidad Dominicana Organización y Métodos O&M con aspiraciones de iniciarnos como Ingeniero en Sistemas y Computación. tipos de algoritmos de búsqueda y ordenación así como sus aplicaciones. Para poder aplicar el nuevo problema aproximado. su importancia en el mundo de las aplicaciones para computadoras y el manejo de lógica de programación. ya que por la definición de ajuste maximal. . En ese mismo orden encontraremos las diferentes técnicaspara diseñarlos como son el método de la fuerza bruta. En el siguiente trabajopretendemos presentar una serie de conceptoy definiciones propios del estudio de los Algoritmos. donde daremos los conceptos básicos de semánticay sus tipos haciendo mayor énfasis en la semántica axiomática. normas. Esto es evidente. Específicos : Introducir los conceptos propios sobre Algoritmo. De igual forma podremos ver las definiciones y algunas características. los vértices incidentes a las aristas de M son un recubrimiento de G.

definidos y finitos. Algoritmos + Estructuras de Datos = Programas. significándonos que solo se puede llegar a realizar un buen programa con el diseño de un algoritmo y una correcta estructura de datos. el que tradujo la obra al latín y el inicio con la palabra: Algoritmi Dicit. multiplicar y dividir números decimales. El eje central de esta metodología es el concepto. (Análisis del problema y desarrollo del algoritmo). ). El lenguajealgorítmico es aquel por medio al cual se realiza un análisis previo del problema a resolver y encontrar un método que permita resolverlo. Proporcionar conceptos sobre su análisis y diseño. ya tratado. algoritmo proviene de Mohammed alKhowarizmi.) 3. Aunque la popularización del término ha llegado con el advenimiento de la era informática. 2. inventor de Pascal. búsqueda. Diseño de algoritmo. Modula-2 y Oberon. donde se recogía el sistema de numeración hindú y el concepto del cero. el cual escribió sobre los años 800 y 825 su obra Quitad Al Mugabala. Fue Fibinacci. Proporcionar concepto sobre las técnicas de diseño. el gran matemático griego (del siglo IV antes de Cristo) que invento un método para encontrar el máximo común divisor de dos números. Desglosar sus variantes (ordenación. Ejecución y validación del programa por la computadora. Es un método para resolver un problema mediante una serie de datos precisos. El conjunto de todas las operaciones a realizar y e orden en que se deben efectuarse. 3. Euclides. matemático persa que vivió durante el siglo IX y alcanzo gran reputación por el enunciado de las reglas para sumar. Definir sus tipos y variantes. etc. Marco Historico Un algoritmo es un conjunto de operaciones y procedimientosque deben seguirse para resolver un problema. se considera con Al-Khowarizmi el otro gran padre de la algoritmia ( ciencia que trata de los algoritmos). Expresar el algoritmo como un programa de lenguaje de programación adecuado.y y y y y y Proporcionar una idea de su uso. La palabra algoritmo se deriva del nombre latinizado del gran Matemático Árabe Mohamed Ibn Al Kow Rizmi. Generalidades El programador de computadoras es ante que nada una personaque resuelve problemas. La resolución de un problema exige el diseño de un algoritmo que resuelva el problema propuesto. Un algoritmo es un método para resolver un problema. Visualizar sus ventajas e importancia. (Fase de codificación. El profesor Niklaus Wirth. A la metodología necesaria para resolver problemas mediante programas se denomina Metodología de la Programación. restar. que describe la secuencia ordenada de pasos que conducen a la solución de un problema dado. Los pasos para la resolución de un problema son: 1. por lo que para llegar a ser un programador eficaz se necesita aprender a resolver problemas de un modo riguroso y sistemático. . 2. de algoritmo. Esta ecuación será de una de las hipótesis fundamentales consideradas en esta obra. se le denomina algoritmo. titulo uno de sus mas famosos libros. la traducciónal latín del apellido de la palabra algorismus derivo posteriormente en algoritmo.

si el cliente es solvente entonces la empresa acepta el pedido. La definición de un algoritmo debe definir tres partes: Entrada. 5. En cada problema el algoritmo se puede expresar en un lenguaje diferente de programación y ejecutarse en una computadora distinta. Los pasos del algoritmo son: 1. Un algoritmo debe ser finito. En el algoritmo de receta de cocina citado anteriormente se tendrá: Entrada: ingrediente y utensilios empleados. de modo que sin algoritmo no puede existir un programa.Para llegar a la realización de un programa es necesario el diseño previo de algoritmo. un aspecto muy importante será el diseño de algoritmos. Dada la importancia del algoritmo en la ciencia de la computación. ingles o francés. la solución de un problema se puede expresar mediante un algoritmo. En esencia. En la cienciade la computación y en la programación. Si se sigue un algoritmo dos veces. inicio leer el pedido examinar la ficha del cliente si el cliente es solvente aceptar pedido. Si se sigue un algoritmo se debe terminar en algún momento. cordero). Proceso y Salida. 2. Un lenguaje de programación es tan solo un medio para expresar un algoritmo y una computadora es solo un procesador para ejecutarlo. Redactar el algoritmo correspondiente. o sea. Así. es decir. pero cualquiera que sea el lenguaje. Salida: terminación del plato (por ejemplo. los pasos para la elaboración del plato se realizaran sin importar el idioma del cocinero. Tanto el lenguaje de programación como la computadora son los mediospara obtener un fin: conseguir que el algoritmo se ejecute y se efectúe el proceso correspondiente. Esta examina en su banco de datos la ficha del cliente. se debe obtener el mismo resultado cada vez. en caso contrario. rechazar pedido fin Diseño del Algoritmo: En la etapa de análisis del proceso de programación se determina que hace el programa. En la etapa de diseño se determina como hace el programa la tarea solicitada. Un algoritmo debe estar definido. 3. 4. en una analogía con la vida diaria. una receta de un plato de cocina se puede expresar en español. en caso contrario rechazara el pedido. Proceso: elaboración de la receta en la cocina. la . Los métodos mas eficaces para el proceso de diseño se basan en el conocido por Divide y Vencerás. Los algoritmos son independientes tanto del lenguaje de programación en que se expresan como de la computadoraque lo ejecuta. los algoritmos son más importantes que los lenguajes de programación o las computadoras. El diseño de la mayoría de los algoritmos requiere creatividady conocimientos profundos de la técnica de la programación. debe tener un numero finito de pasos. Características de los Algoritmos: Las características fundamentales que debe cumplir todo algoritmo son: y y y Un algoritmo debe ser preciso e indicar el orden de realización de cada paso. Ejemplo de Algoritmo: Un cliente ejecuta un pedido a una fábrica. sin embargo. por ejemplo. el algoritmo será siempre el mismo.

Cualquier programa bien diseñado consta de un programa principal (el modulo de nivel mas alto) que llama a sub programas (módulos de nivel mas bajo) que a su vez pueden llamar a otros sub programas. Recursos consumidos: Tiempo de ejecución. Recursos consumidos: Ejemplo. Cada sub programa es resuelto mediante un modulo (sub programa) que tiene un solo punto de entrada y un solo punto de salida. comprobados y depurados independientemente (incluso por diferentes programadores) y a continuación combinarlos entre si. Criterio empresarial: Maximizar la eficiencia.resolución de un problema complejo se realiza dividiendo el problema en sub problemas y a continuación dividir estos sub problemas en otros de nivel mas bajo. robusto. Los programas estructurados de esta forma se dice que tienen un diseño modular y el método de romper el programa en módulos más pequeño se llama Programación Modular. depurar el modulo. El proceso de romper el problema en cada etapa y expresar cada paso en forma más detallada se denomina refinamiento sucesivo. Comprobar el modulo. Si es necesario. fácil de entender. Los módulos pueden ser planeados. Este método se conoce técnicamente como diseño descendente (Top Down) o modular. su facilidad de programarlo. 4. Un algoritmo es mejor cuantos menos recursos consuma. etc. Análisis De Algoritmos Recursos De Computadores Y Complejidad Algoritmo: Conjunto de reglas para resolver un problema. forma aproximada o algunos casos. codificados. El proceso implica la ejecución de los siguientes pasos hasta que el programa se termina: y y y y programar modulo. El diseño del algoritmo es independiente del lenguaje de programación en el que se vaya a codificar posteriormente. Eficiencia: Relación entre los recursos consumidos y los productos conseguidos. hasta que pueda ser implementada una solución en la computadora. Memoria principal: Entradas/salidas a disco. El proceso que convierte los resultados del análisis del problema en un diseño modular con refinamiento sucesivo que permitan una posterior traducción al lenguaje se denomina diseño de algoritmo. procesadores. Combinar el modulo con los módulos anteriores. etc. ¿Cuántos recursos de tiempo y memoria consume el siguiente algoritmo sencillo? i:= 0 a[n+1]:= x repetir i:= i + 1 . corto. Su ejecución requiere unos recursos. Lo que se consigue: Resolver un problema de forma exacta. Comunicaciones.

. Media de todos los posibles contenidos. Asignación de tiempos. Conclusión: Estudiar la variación del tiempo y la memoria necesitada por un algoritmo respecto al tamaño de la entrada y a los posibles casos. Normalmente usaremos la notación T(N)=. En particular.1 ms N= 5. El ordenador donde lo ejecutemos: 286. Contenido de los datos de entrada.2 s .hasta a[i] = x Respuesta: Depende..): Una unidad de tiempo. ¿De qué depende? De lo que valga n y x. T(N) = bN + c. En general los recursos dependen de: Factores externos. con los límites del FOR. para el conteo de instrucciones.? Sabemos que cada ejecución lleva un tiempo constante. La implementación que haga el programador del algoritmo.. T(N) = 2N + 4. Pentium III. T(6)= 0... Mejor caso. de los tipos de datos. Cray..exe": N= 4. externos no aportan información sobre el algoritmo. El lenguaje de programación y el compilador usado.. :=. pero ¿qué significa T(N)? Tiempo de ejecución en segundos. Los factores externos no aportan información sobre el algoritmo... T(5)= 5 ms N= 6. Instrucciones ejecutadas por el algoritmo. T(4)= 0. Caso promedio. ¿Tardarán todas lo mismo? Ejecuciones del bucle principal. T(N) = N+1. -. Bucles WHILE y REPEAT: Estudiar lo que puede ocurrir. Ejemplo. o una constante diferente. Programa "cifras. Mejor caso y peor caso según la condición. Algunas reglas básicas.. de las estructuras de datos utilizadas. Ejemplo.. de la máquina.. IF y CASE: Estudiar lo que puede ocurrir. Operaciones de entrada salida: Otra unidad de tiempo. Peor caso. La ejecución más lenta posible. Operaciones básicas (+. o alguna constante. con los segundos que tardan las operaciones básicas correspondientes. ¿Existe una cota inferior y superior del número de ejecuciones? ¿Se puede convertir en un FOR? El análisis de algoritmos también puede ser a posteriori: implementar el algoritmo y contar lo que tarda para distintas entradas. Calcular la media de una matriz de NxM. Bucles FOR: Se pueden expresar como una sumatoria. ¿Cuánto tiempo. de lo que haya en a. cuántas instrucciones.. Suponiendo que b y c son constantes. Tamaño de los datos de entrada.. ¿Se puede predecir cuándo se cumplirán las condiciones? Llamadas a procedimientos: Calcular primero los procedimientos que no llaman a otros. luego se diferencia en una constante con los anteriores. de forma aproximada (y parametrizada). *. El contenido favorece una rápida ejecución.

Podemos comparar con otros algoritmos. Si f Î O(g) entonces O(f) Í O(g). si el algoritmo es poco eficiente. para valores de n suficientemente grandes. "Valores de n sufic.": nos quitamos las constantes. ¿Cómo es la relación para los W ? P3. T(8)= 3. g)). llamamos orden de f al conjunto de todas las funciones de N en R+ acotadas superiormente por un múltiplo real positivo de f. La definición es aplicable a cualquier función de N en R. 2n+1 Î O(n). "Funciones acotadas superiormente por un múltiplo de f.g) = O(max(f. W (f)=W (g). W (T): Orden inferior de T. Q (f)=Q (g) g(n) ii) limn¥ ® f(n) = 0 Þ O(f) Í O(g). Dadas f y g de N en R+. -g))? P5. no una función. Si f Î W (g) y g Î W (h) entonces f Î W (h) Ej. u omega de T. Orden de complejidad de f(n): O(f) Dada una función f: N ® R+.) es completa? Dadas f y g. Nos interesa un análisis que sea independiente de esos factores. $ n0 Î N. no sólo tiempos de ejec. W (f+g) = W (max(f+g)) ¿Y para los Q (f+g)? ¿Es cierto que O(f . se cumple: i) O(f) = O(g) Û f Î O(g) y g Î O(f) ii) O(f) Í O(g) Û f Î O(g) ¿La relación de orden entre O(. para valores suficientemente grandes (asintóticamente) sin considerar constantes.. T(7)= 10 s N= 8.N= 7. Propiedades P1. Podemos hacer previsiones. W (g) Í W (f) g(n) . ¿se cumple O(f)Í O(g) ó O(g)Í O(f)? P4... " n ³ n0: t(n) £ c·f(n) } Nota: O(f) es un conjunto de funciones. Dadas f y g. se cumple: i) limn¥ ® f(n) Î R+ Þ O(f)=O(g). de N en R+. O(f)= { t: N ® R+ / $ c Î R+.. n Î O(n2) Þ 2n+1 Î O(n2) P2.5 min ¿Qué conclusiones podemos extraer? Análisis a priori: Evitamos la implementación. Q (T): Orden exacto de T. Dadas f y g de N en R+. Medidas Asintoticas Notación asintótica: El tiempo de ejecución T(n) está dado en base a unas constantes que dependen de factores externos.": no nos importa lo que pase para valores pequeños. Grandes.. Si f Î O(g) y g Î O(h) entonces f Î O(h). Notaciones asintóticas: Indican como crece T. O(T): Orden de complejidad de T. O(f+g) = O(max(f.

. Ejemplo. ¿Qué relación hay entre los siguientes órdenes? O(n+m).. se cumple: i) limn¥ ® f(n) Î R+ Þ O(f) = O(g) g(n) ii) limn¥ ® f(n) = 0 Þ O(f) Ì O(g) g(n) iii) limn¥ ® f(n) = +¥ Þ O(f) É O(g) g(n) Notación con varios parámetros: En general. ... M(B.xN ® R+) Ej. o variables T(N.m.. nm) suficientemente grandes.P5. nm): O(f) Dada una función f: Nm ® R+. k2 ³ n2 . O(n+2m) Notaciones condicionales: En algunos casos interesa estudiar el tiempo sólo para ciertos tamaños de entrada. tenemos W (f | P) y Q (f | P). ‡Relación de orden entre O(. a. llamamos orden de f según P (o condicionado a P) al conjunto: O(f | P)= { t: N ® R+ / $ c Î R+. k) = kB+l+n+2kn Orden de complejidad de f(n1. Ej. Ejemplo. Para cualquier f y g. para valores de (n1... ¿O(f) « O(f | P)? Ordenes De Complejidad Uso de los órdenes de complejidad: Dado un tiempo t(n). y que más se aproxime asintóticamente. k2.) = Relación de inclusión entre conjuntos. O(f)=O(g) Û Q (f)=Q (g) Û f Î Q (g) Û W (f)=W (g) P7..b). T(N) = T(N.. el tiempo y la memoria consumidos pueden depender de muchos parámetros.. .. Memoria en una tabla hash.. b) = a·N + b El tiempo depende del tamaño del problema N. l.. encontrar la función f más simple tal que t Î O(f). . " k1 ³ n1 . para funciones con varios parámetros.." km ³ nm : t(k1. llamamos orden de f al conjunto de todas las funciones de Nm en R+ acotadas superiormente por un múltiplo real positivo de f. podemos extender los conceptos de W (f) y Q (f). O(nm) O(n2). . O(f)= { t: Nm ® R+ / $ c Î R+. k2. Podemos suponerlos constantes T(N)... O(f) = O(f | true). nm Î N.. t(n) = 2n2/5 + 3p /2.. n2.a.. Algoritmo de búsqueda binaria: Si N es potencia de 2 el estudio se simplifica.. km) £ c·f(k1. Orden condicionado de f(n): O(f | P) Dada una función f: N ® R+.. Las propiedades se siguen cumpliendo ® Demostrarlo.n. km) } De la misma forma. f Î O(g | false). Ejemplo. y del tiempo de inicialización b y de ejecución de un paso a. . ¿Qué relación hay entre O(log2 n) y O(log10 n)? P6. f: Nm ® R+ (f: Nx. n2. t(n) Î O(n2). y P: N ® B. " n ³ n0: P(n) Þ t(n) £ c·f(n) } De igual forma. Dadas f y g de N en R+.. $ n0 Î N. Dadas f y g de N en R+. $ n1.

aparecerá un orden logarítmico O(log2 n).. El acto de diseñar un algoritmo puede considerarse como una tarea que difícilmente podrá ser del todo . Relación de orden: igual que antes.. llamamos omega de f al conjunto de todas las funciones de N en R+ acotadas inferiormente por un múltiplo real positivo de f. asintóticamente y salvo constantes.) Ì O(n2) Ì O(n3) Ì . para valores de n suficientemente grandes. Los logaritmos son del mismo orden. llamamos orden exacto de f al conjunto de todas las funciones de N en R+ que crecen igual que f. å im Î O(nm+1) i=1 i=1 i=1 Si hacemos una operación para n. siendo c y d constantes positivas. $ n0 Î N. +a1n + a0 t(n) Î o(amnm) ¹ o(nm) ¿o(amnm) Í O(amnm)? ¿o(t) Í O(t)? Costa de complejidad con frecuencia Algunas relaciones entre órdenes frecuentes: O(1) Ì O(log n) Ì O(n) Ì O(n·log n) Ì O(n·(log n)2) Ì O(n1. si p y q son polinomios del mismo grado.. å i = n(n+1)/2 Î O(n2).. Ejemplo. Orden inferior u omega de f(n): W (f): Dada una función f: N ® R+.+a1x+a0 es O(xn). O(c) Ì O(n) O(cn + b) = O(dn + e) O(p) = O(q). $ n0 Î N.. t(n) = amnm + am-1nm-1 + . llamamos o pequeña de f al conjunto de todas las funciones de N en R+ que crecen igual que f asintóticamente: o(f)= { t: N ® R+ / lim t(n)/f(n) = 1}n¥ ® Esta notación conserva las constantes multiplicativas para el término de mayor orden. t Î O(g) ‡Se cumple que: O(c) = O(d). Q (f) = O(f) Ç W (f) = { t: N ® R+ / $ c.. " n ³ n0: c·f(n) ³ t(n) ³ d·f(n) } Notación o pequeña de f(n): o(f): Dada una función f: N ® R+. Ì O(2n) Ì O(n!) Ì O(nn) ¿Qué pasa con las omegas? ¿Y con los órdenes exactos? El orden de un polinomio anxn+. W (f)= { t: N ® R+ / $ c Î R+.±O(f) £ O(g) Û O(f) Í O(g) Û Para toda t Î O(f).. nnn å 1 = n Î O(n). " n ³ n0: t(n) ³ c·f(n) } La notación omega se usa para establecer cotas inferiores del tiempo de ejecución. 5.001. Orden exacto de f(n): Q (f): Dada una función f: N ® R+. .. Técnica de diseño de algoritmos Diseño de Algoritmos: Hasta ahora se han realizado algunos comentarios respecto a la necesidad de diseñar algoritmos correctos y eficientes utilizando los elementos de un lenguaje de programación .. d Î R+.. independientemente de la base.. otra para n/2. O(p) Ì O(q).Es necesario en este momento mencionar algo sobre como hacerlo. n/4. si p es un polinomio de menor grado que q.

que debe . Nos estamos refiriendo a métodos basados en la mejora de la eficiencia (por ejemplo. siendo dicha solución finalmente adaptada al dominio original. pero con un poco de análisis puede encontrarse algoritmos más eficientes. hay problemas cuya solución no puede hallarse sino mediante un proceso de búsqueda. El conocimiento de técnicas de diseño es solo un primer paso para el diseñador. La investigaciónen esta área ha permitido descubrir un conjunto de métodos o esquemas de diseño hacia los cuales puede orientarse la realización de muchos algoritmos. Supongamos que disponemos de una especificación precisa. Todo problema algorítmico es un reto para su diseñador. Este método. puede ser muy directo. a pesar de lo complejas que son las operaciones de búsqueda. No obstante. idear un algoritmo continua siendo una labor bastante creativa donde los conocimientos y la experiencia del propio diseñador tiene un papel fundamental. Una forma de facilitar esta labor consiste en recurrir a técnicas conocidas de diseño de algoritmos. El diseño de un algoritmo que resuelva un problema es. conviene conocer otros métodos de diseño de algoritmos que también resultan de utilidad práctica. dados uno datos de entrada valido. Otros esquemas requieren un análisis minucioso del problema de forma que la solución se vaya construyendo en etapas. Si no nos importa la eficiencia del algoritmo. Aprender los principiosbásicos del diseño de algoritmos podemos preguntarnos por un método aceptable. si la decisión en una etapa. a la vez bastante ineficiente. llamado de fuerza bruta. Aun así. y quizás el mejor. Se programa un computador de manera que parta de un conjunto de axioma matemáticos y los que use para reducir aleatoriamente teoremas validos. la solución es dinámica. una tarea difícil. Si puede preverse que decisión conviene en cada etapa para producir cierto tipo de mejor resultado. y a métodos basados en transformaciones del dominio para encontrar una solución mas fácilmente a un problema en un dominio transformado.automatizada. y el empleode tablas como estructura auxiliar para la resolución eficiente de problemas donde se aplica programación dinámica). en general. Muchos problemas pueden resolverse buscando una solución fácil y directa pero. puesto que existe un número reducido de esquema y técnicas de diseño. es organizar el diseño sobre un esquema de algoritmo o una técnica de diseño que haya demostrado su utilidad para otros problemas. algunos resultan inmediatos de resolver. se decir. completa y consistente del problema a resolver y queremos obtener un algoritmo en el que. su tarea se simplifica. podríamos utilizar un algoritmo general llamado algoritmo del museo británico. solo puede tomarse tras considerar varias solucionesde otras etapas mas simples. tenemos una solución voraz. a esquemas muy generales que pueden adaptarse a un problema particular al detallar las partes generales del esquema. se produzca cierto resultado. Por ultimo. El mas entendido. otros son bastante complejos. Este método de trabajo es practicable. basado en la descomposición de un problema en subproblemas. El esquema mas sencillo quizás sea el llamado divide y vencerás. el uso de parámetros de acumulación al resolver problemas utilizando divide y vencerás. y a pesar de que resulta mas adecuado en bastantes casos utilizar alguno de estos esquemas que realizar un diseño desde cero. su uso adecuado mediante el esquema de búsqueda con retroceso (o backtracking) permite ganar gran eficiencia respecto a soluciones de fuerza bruta. Consideraciones generales Si el hábil programador dispone de un recetario de algoritmos de donde poder seleccionar el más adecuado para cada problema.

poco reflexionada. Ejemplo: Números de Fibonacci Los números de fibonacci suele especificarse como: Fib(0)=1 Fib(1)1 Fib(n+2)=fib(n)+fib(n+1) Esta especificación de los números de fibonacci tienen una formulación recursiva inmediata en estilo funcional. En realidad. Cada una se ilustra con un ejemplo distinto. en caso positivo. Los parámetros adicionales tienen como misión ir acumulando resultados principales durante el proceso recursivo. es muy probable que no se hayan aprovechado propiedades deducibles del problema y que la solución sea terriblemente ineficiente. Método de fuerza bruta Comenzamos el estudio de esquemas algorítmicos con un método sencillo. la fuerza bruta. Uno de ellos realizaba una búsqueda secuencial con complejidad lineal sobre el tamaño del vector y podía usarse con cualquier vector. una solución funcional a muchos problemas. Parámetros Acumuladores Veamos primero una solución ineficiente que intentaremos mejorar. Técnicas de los Parámetros Acumuladores y de Tabulacion La recurcion es un mecanismo que permite obtener. Una solución por fuerza bruta también puede resultar adecuada como primera aproximación a la solución final. dichos algoritmos pueden servir como una primera aproximación al algoritmo definitivo. Un modo de evitar problema lo proporciona la técnica de los parámetros acumuladores. si no mas bien calificativo Para una forma de diseñar algoritmos: tomar una solución directa. Lo más razonable es comprobar si el vector esta ordenado y. Otro algoritmo realizaba un búsqueda dicotomica o binaria. En estos casos. pero dado que no se ha analizado apenas el problema. Por ejemplos: Algunos algoritmos de búsqueda de un elemento en un vector. Muchos algoritmos recursivos resultan eficientes. con la experiencia.completarse con otros conocimientos y. pero muy ineficientes. pero no todos: hay algunos fácilmente formulables. por lo que uno puede sentirse tentado a usar siempre. pero debe mejorar su rendimiento para que sea práctico. dad su ineficacia. aprovechar esta circunstancia para usar el algoritmo más eficiente: el de búsqueda binaria. . pero poco reflexionada. Esta es la solución de fuerza bruta: una solución directa. cuya idea básica se expone a continuación. El algoritmo primero responde a un razonamiento más sencillo. esto no es malo. En principio. con complejidad logarítmica. pero que debe evitarse siempre que se pueda. La función principal simplemente realiza una llamada a esta función auxiliar en los que los parámetros de aquellas se modifican y los parámetros nuevos toman un valor inicial adecuado . en combinación con otras contrucciones. Veremos dos parámetros para la mejora de eficiencia de algoritmos recursivos: el uso de parámetros acumuladores y el uso de tablas. y solo se podía usar cuando el vector estuviese ordenado. La función principal usa una función auxiliar que tiene los parámetros de aquellas más algunos adicionales. no es un esquema algorítmico. sobre todo. porque su desarrollo puede permitir profundizar más sobre el problema y conocer propiedades que sean utilizadas para obtener otra versión más eficiente.

La estrategia voraz aplicada comienza devolviendo. se almacena en una tabla.etc. Búsqueda de una palabra en un diccionario Como ejemplo sencillo de aplicación de esta estrategia puede considerarse la búsqueda de una palabra en un diccionariode acuerdo con el siguiente criterio. la planificación en el orden de la ejecución de unos programas en un computador. Ejemplo: Sea el problema de la competición. Consideraciones y Criterios para Diseñar Algoritmos Algunas consideraciones estilísticas pueden contribuir a mejor la calidadde los algoritmos (y programas ) mediante la reducción del numero de errores que aparecen al desarrollar los. Suponiendo que se disponga de cantidad suficiente de ciertos tipos diferentes de monedas de curso legal. Puede emplearse en problemas de optimización. resolver independientemente los subproblemas para luego combinar sus soluciones y obtener la solución del problema original. la modificación para incorporar probabilidades diferentes es evidente y no complica el problema. La intención es que la primera vez que se realiza un cálculo.Tabulacion No todos los algoritmos recursivos ineficientes pueden optimizarse con la técnica de los parámetros acumuladores. Otra técnica útil es el uso de tablas. De forma que cada uno tiene un 50% de posibilidades de ganar cada partido. . El procedimiento se repite sucesivamente hasta encontrar la palabra o decidir que no aparece. De todas formas. cuando se pueda. no importa que). A. Si no ha encontrado y es anterior se procede a buscarla en la primera mitad. continua aplicándose el mismo criterio para la segunda moneda mas valiosa. como el conocido de la mochila. se va procedimiento paso a paso realizándose la mejor elección (usando una función objetivo que respeta un conjunto de restricciones ) de entre las posibles. la búsqueda en estructuras ordenadas.etc. si es posterior. y así sucesivamente. Ejemplo. Esta técnica se puede aplicar con éxito a problemas como la multiplicación de matrices. se trata de dar como cambio la menor cantidad posible usando estos tipos de monedas.B. en la búsqueda de caminos mínimos sobre grafos. Método voraz: Este método trata de producir tipo de mejor resultado a partir de conjunto de opciones candidatas . mientras el valor de dicha moneda sea mayor o igual al cambio que resta por dar). Hay dos participantes (deportistas o equipos. donde puede consultarse otras veces que se necesite. Esta técnica también se suele emplear con la programación dinámica. El proceso finaliza cuando se ha devuelto todo el cambio. Ejemplo. en una maquina expendedora de tabaco). la moneda de mayor valor ( es decir. Divide y vencerás: Consiste en descomponer un problema en un subproblema.. se buscara en la segunda mitad. Dar un cambioutilizando el menor número de monedas Considérese ahora el problema de la devolución del cambio al realizar una compra (por ejemplo. que juegan una competición que es ganada por el primero que venza en n partidos. se supone que ambos participantes tienen cualidades y preparación similar .Para ello. Se abre el diccionario por la pagina centrar(quedando dividido en dos mitades) y se comprueba si la palabra aparece allí o si es léxico gráficamente anterior o posterior. la ordenación de vectores. siendo ( n ) mayor que( 0 ). Por sencillez .

En realidad. Se supone que un problema de esta clasetiene al menos una solución. la calidad de un algoritmo tiene muchas facetas y todas ellas importantes. 4.. La eficiencia de un algoritmo se mide por los recursos que este consume. Ante la pregunta ¿Cuáles son las característica de un buen algoritmo?. El modo de encolumnar las distintas partes de un algoritmo para facilitar su lectura y comprensión. A pesar de que con la reducción de los costes del hardware es posible diseñar computadores más rápidos y con más memoria. cierta medida. La documentación ayuda a comprender el funcionamiento de los algoritmos. Corrección. Claridad. no hay que desperdiciar estos recursos y tratar de desarrollar algoritmos más eficientes. lo ideal es que nuestro algoritmo resulte correcto. subprogramas. Generalmente. en cuyo caso no importa cual se elija. La dificultad principal para resolver esta clase de problemas estriba en el análisis necesario para poder formular un algoritmo que halle la solución en varios pasos. eficiente. y de acuerdo con los puntos de vista anteriores. el algoritmo debe estar bien documentación. estos problemas no se intentan resolver "de golpe ". sea el problema de encontrar un subconjunto de los arcos de un grafo.También influyen haciendo que nuestro algoritmo resulten más fáciles de leer y entender para otras personas. Ciertos detalles o algunas partes especiales de los mismos pueden olvidarse fácilmente o quedar oscura si no están adecuadamente comentadas. analizando durante cada etapa que elemento conviene añadir a la solución parcial ya existente. A menudo. Normalmente. el algoritmo debe funcionar. Esta característica hace que aunque el análisis del problema sea arduo. estas normas de estilo se dirigen hacia aspectos como la forma de construir los nombres de variables o tipo de datos que aparezcan. Nunca se debe olvidar que la característica más simple e importante de un algoritmo es que funcione. Algoritmos voraces Esquema voraz Hay muchos problemas en los que se pretende obtener un subconjunto de n elementos que satisfaga ciertas restricciones y que optimice alguna medida. 2. Otro ejemplo se da cuando. el algoritmo no debe desaprovechar recursos. la tipografía seguida ala hora de escribir nombres de variables. Ello asegura que tanto algoritmos como programa resulten legibles y puedan modificarse fácilmente en caso de necesidad. encontrando de una sola vez la solución completa y óptima. Eficiencia. 1. Puede haber varias soluciones optimas. Los criterios de estilo pueden reflejarse en un conjunto de normas de estilo de codificación. Pude aparecer obvio. Por ejemplo. 3. la solución voraz siempre . se habla de la memoria y del tiempo de ejecución . Estilo y calidad de los programas van fuertemente unidos. Resumiendo. Es más frecuente que el subconjunto de la solución se vaya formando paso a paso. los factores que identifican la calidad en ellos . Un algoritmo voraz sigue el esquema anterior. fiable y fácil de mantener. dados unos ficheros almacenados en una cinta de que el tiempo de recuperación de un fichero cualquiera sea el mínimo en promedio. pero con la fortuna de que cada vez que añade un elemento a la solución se tiene la certeza de haber realizado la mejor elección posible. etc. y la normas sobre como y donde deben de introducirse los comentarios. el problema incluye restricciones adicionales que limitan el número posible de soluciones. En particular. claro. palabras claves. las siguientes respuestas reflejan. pero resulta difícil de asegurar en algoritmos complejos.

el candidato se incorpora definitivamente. el mejor candidato. debe recordarse que puede haber varios criterios alternativos de selección y que de su . el conjunto de candidatos que forman la solución está vacío. Al contrario. se desecha el candidato. De todas formas.resulte sencilla. la solución consta de: y y y Un conjunto de candidatos Una función de selección que en cada momento determine que candidato de los aún no usados parece ser el mejor. pero si la función de selección es la adecuada. En cada paso se intenta añadir el mejor de los candidatos restantes a dicha solución parcial. Obsérvese que las funciones de validez y completitud no se preocupan de la optimalidad del la solución. si satisface las restricciones del problema y. Por tanto. es definitiva. es decir. si permite formar alguna solución del problema. por tanto. solución v (siguiente)) VorazAcumulador (candidatos ± (siguiente). nunca cambian de opinión: una vez que un candidato es aceptado o rechazado en la solución.n ) : ( 1. A su vez. Podemos representar el esquema voraz de la siguiente forma funcional: FUNCTION Voraz ( candidatos: ( 1.. el problema parte de: y y Una función objetivo que da el valor de una solución.. puede llamarse candidato al elemento tratado en cada paso. sino que se utiliza durante el análisis del problema y es determinante en la elección de la función de selección. La función objetivo no suele aparecer en el algoritmo final. Por lo que se ha descrito del esquema voraz. Si este conjunto ampliado sigue siendo válido. la dificultad principal al diseñar un algoritmo voraz reside en encontrar un criterio en encontrar un criterio de selección que garantice la optimalidad de la solución. éste es un proceso repetitivo sencillo que trata sucesivamente los diferentes elementos del problema.n) : (1. La única complicación es comprobar que se siguen satisfaciendo las restricciones del problema. Para facilitar la descripción de este proceso. permite formar una solución del problema. Según esta descripción. cada solución válida y completa es optima. Obviamente. Inicialmente. Solución : (1. si dicho conjunto no es válido..n). la primera solución encontrada es óptima. es decir. Si el algoritmo voraz se ha diseñado correctamente. solución) VorazAcumulador (candidatos. Además. Una función que determine si cierto conjunto de candidatos es válido. ésta es la función por optimizar.n) -> FUNCTION VorazAcumulador ( candidatos : (1. ( ) ) Puede verse por qué estos algoritmos se llaman " voraces " : en cada paso toman el mejor trozo de la solución.. Un conjunto de restricciones sobre el valor de los datos de entrada y sobre la solución final del problema.n) -> Cadidatos = ( ) v EsSolución ( solución)-> Value siguiente -> seleccionar ( candidatos ) IN EsVálida (solución v ( siguiente)) => VorazAcumulador (candidatos ± (solución). es decir.. la decisión.

Además. Su declaración es la siguiente: TYPE Monedas -> M500 I M100 I M50 I M25 I M5 I M1. Como ejercicio. mientras sea posible. Además. la moneda de mayor valor de entre las candidatas. y cuyo valor total es igual al importe a desglosar. La función objetivo cosiste en minimizar la cantidad total de monedas utilizadas en el desglose. Asimismo. cuando un candidato (moneda) se incorpora al conjunto solución. y de un importe. en particular. se considera el problema de un cambio o desglose en monedas. Desglose en monedas Como primer ejemplo introductorio sencillo al que puede aplicarse la técnica voraz. Con esta información se puede comprobar que en este problema están presentes los distintos elementos de la técnica voraz. de las que se supone que hay cantidad suficiente para realizar el desglose. Hay que desglosar una cantidad en un conjunto de monedas tratando de cumplir alguna condición. La función de selección establece que hay que elegir. ¥ ¥ . este algoritmo tiene la ventaja de valer para las situaciones en que el número de participantes no es una potencia de dos. 25. en este caso. podemos utilizar sólo monedas de 500.correcta elección depende que la solución calculada por el algoritmo sea optima. suponemos que manejamos dineroespañol y. Es fácil encontrar una solución si en cada etapa se genera el subcalendario correspondiente a un equipo. es decir. Valores -> Integer M500 M1 Cantidades -> Integer M500 . tales que sumados sus valores equivalgan al importe. la tabla de competición se va completando por filas. La condición de factibilidad de la solución siendo construida establece en el desglose debe ser menor o igual que el importe a desglosar. 50. Divide Y Vencerás La técnica divide y vencerás consiste en descomponer el problema en un conjunto de subproblemas más pequeños. utilizar el menor número de monedas. Para ello. 5 y 1 pesetas para el desglose. 100. Una solución viene dad por un conjunto de monedas devuelto tras el desglose. Los elementos de la técnica voraz están presentes en este problema de la siguiente forma: y y y y y El conjunto de candidatos está constituido por cada una de las monedas de los diferentes tipos que se pueden usar para realizar el desglose del importe dado. Después se resuelven estos subproblemas y se combinan las soluciones para obtener la solución para el problema original. Cada fila resultante puede tener una complejidad de o (n2).M1 Se supone inicialmente asignados los valores a cada uno de los tipos de monedas. éste no será nunca excluido de él. se parte de un conjunto de tipos de monedas válidas. se declaran los tipos VALORES y CANTIDADES para representar el valor asignado a cada unidad monetaria y la cantidad de cada tipo de moneda que se devolverá en el desglose. Para simplificar. Estos valores se definen por medio de un tipo enumerado MONEDAS. el lector puede intentar encontrar una solución voraz del problema del calendario. Como fila primera se toma la secuencia de los índices de los participantes en cualquier orden. Se trata de indicar la cantidad (menor) de monedas de los tipos considerados.

medio. es fácil su generalización a k subproblemas 2<k<=n. inferior. medio+1. superior) THEN ResolverDirectamente (problema. en la que se utiliza un vector de tamaño N. N. olución) ELSE Medio := Partir (inferior.. 1. subproblema2) => Combinar (DivideYVenceras (subproblema1) . considerado el problema como de tipo dato y la solución..n. solución) DyVAux (problema. Veamos el esquema de divide y vencerás para dos subproblemas. superior. Este esquema de partición de problemas se denomina esquema de divide y vencerás solo en el caso en que los problemas sean de la misma clase del problema original. solución) . IN inferior. Sin embargo. Mas formalmente. TYPEVAR dato. OUT solución : resultado) -> VAR medio: 1.N subsolucion1. Por supuesto.. DyVAux (problema. inferior. el proceso recursivo nunca terminaría. DyVAux (problema. se descompone en varias partes más fáciles de resolver. la técnica de divide y vencerás parte la entrada en k subproblemas. Su formación funcional es como sigue. 1<k<=n. en caso contrario. subsolucion2). El caso más frecuente es cuando el número de subproblemas es dos. La técnica de divide y vencerás es quizás una de las utilizadas debido a su sencillez: si un problema es demasiado grande para resolverlo de una vez.n..Esquema de Divide y vencerás. subsolucion2. DivideYVenceras (subproblema2)) Se puede hacer una formulación imperativa similar. Esta restricción permite una formulación y resolución recursiva de los subproblemas.N. resultado FUNCTION DivideYVenceras (problema : dato) : resultado -> EsPequeño (problema) }=> ResolverDirectamente (problema) | VALUE subproblemas -> Partir (problema) IN subproblemas == (subproblema1. Estos subproblemas se resuelven independientemente y después se combinan sus soluciones parciales para obtener la solución del problema original. OUT solución : resultado) -> PROCEDURE DyVAux (IN problema : dato1. superior. subsolucion2 : resultado IF EsPequeño (inferior. superior). Combinar (subsolucion1. escribiremos una formulación más restrictiva pero bastante usual. de tipo resultado: TYPEVAR Dato. subsolucion1). resultado PROCEDURE DivideYVenceras (IN problema : dato1. dado un problema al resolver planteando en términos de una entrada de tamaño n. deben existir algunos pasos sencillos cuya solución pueda calcularse fácil y directamente. superior : 1.

contiene el numero del participante contra el que el participante i-esimo compite el día j-esimo. 1<=i<=n. el tiempo de cómputo de la función DivideYVecneras se describe con la siguiente relación de recurrencia: g(n). puede suponerse que las competiciones se celebran en días sucesivos y que cada participante compite una vez por día. Se supone también que cada participante tiene asignado un número comprendido entre 1 y N. el conjunto P(i) de todas las permutaciones posibles del resto de los participantes con los que debe competir. resultan nx(n-1)!=n! formas de rellenar la tabla. para nuestros propósitos resulta indiferente el deporteobjeto de la competición. se supone que el numero de participantes es una potencia de dos. El método de fuerza bruta resulta sencillo.. es decir. la solución del problema puede representarse en una tabla de dimensión nx(n-1). La eficiencia final del algoritmo depende de la función f(n) concreta que aparezca durante el análisis. Cada conjunto P(i) consta de (n-1)! Elementos. Por tanto. Obsérvese que los números de participantes incluidos en la fila i de la tabla son distintos porque el participante i-esimo solo debe competir una vez con cada participante restante. pero es terriblemente ineficiente. es decir. Se dispone de una solución inmediata aplicando fuerza bruta. 1<= i<=n. en caso contrario donde T(n) es la función de tiempo de DivideYVenceras para entradas de tamaño n. Primero se obtiene para cada participante i. Elaboración de un Calendario Deportivo: Sea un campeonato deportivo. Para simplificar el problema. El elemento (i. es general. Sin embargo la aplicación de la técnica de divide y vencerás produce una solución mas sencillas aun pero muy eficientes. Dado que el numero de participantes de n.n}-{i} ahora se completan las filas de la tabla de todas las formas posibles. incluyendo en cada fila i algún ejemplo de P(i). Se necesitan elaborar n-1 competiciones por participantes. se elige uno cualquiera. La siguiente figura describe visualmente parte de la elaboración de la tabla. A su vez. así que hablaremos de participantes en vez de deportistas o equipos. Nótese que.El esquema general se adapta a un problema concreto al sustituir los metasimbolos EsPequeño. la columna j también contiene números distintos. Por concreción. Solo sirve como solución aquellas combinaciones de fila que cumplan las restricciones enunciadas en el párrafoanterior sobre las columnas de la tabla (las restricciones sobre las filas están garantizadas por el modo de generar los conjuntos P(i)). días . y sin perdida de generalidad. Partir y Combinar por funciones o procedimientos concretos. Si el tamaño de los dos subproblemas es el mismo (o casi). ResolverDirectamente. g(n) es el tiempo que tarda la función ResolverDirectamente en resolver problemas de pequeño tamaño (normalmente una constante) y f(n) es el tiempo necesario para partir el problema y combinar las subsoluciones. El problema consiste en elaborar un calendario de competición de forma que cada participante compita exactamente una vez con cada uno de los demás participantes. para que esta técnica resulte eficiente todos los subproblemas deben ser de tamaño parecido. hay n = 2k participantes para algún entero positivo k.si n es pequeño T(n) = 2 T(n/2) + f(n). 1<=j<n. Si hay varios calendarios validos.j)±esimo de la tabla. porque el día j-esimo cada participante solo puede competir con otro participante. el conjunto de permutaciones de los números {1.

PROCEDURE Calendario ( INOUT tabla : (1. La solución es directa porque se celebra una sola competición entre ambos..N..1. la unión de estos subcalendarios no forma un calendario completo para el campeonato de 2k participantes...1 participantes 1 2 2 1 1 2 3 1 2 3 4 2 1 4 3 3 4 1 2 4 3 2 1 1 2 3 4 5 6 7 1 2 3 4 5 6 7 8 2 1 4 3 8 5 6 7 3 4 1 2 7 8 5 6 4 3 2 1 6 7 8 5 5 6 7 8 1 2 3 4 6 5 8 7 4 1 2 3 7 8 5 6 3 4 1 2 8 7 6 5 2 3 4 1 Se distinguen dos casos. El algoritmo descrito se expresa a continuación.2n .N)1. IN sup :1. El calendario de los participantes de numeración superior se completa de forma similar con los números de los participantes de numeración inferior. superior en orden creciente de numeración. El subcalendario del primer participante es sencillo porque basta con que compita en días sucesivos con los participantes de numeración.N. El siguiente participante toma esta secuencia y realiza una fácil permutación de la misma que le garantiza el respeto de las restricciones de la solución. rotando dicha secuencia a la derecha.N-1) -> VAR ¦ . Este proceso se repite para el resto de los participantes de numeración inferior. Por fortuna. es decir. cuando hay más de dos participantes. El problema puede reducirse a dos sub problemas de tamaño 2k-1 si se elaboran independientemente dos subcalendarios de tamaño 2k x(2k-1 -1): uno para los participantes. ya que a unión de los dos calendarios tiene un tamaño 2k x(2k-1 -1).N) 1.. el resto del calendario se puede construir fácilmente. para k>1. OUT tabla : (1. puede decirse que el "tamaño" del problema es 2k (sabemos que el calendario tendrá un tamaño de 2k x(2k-1 -1) posiciones). faltan por elaborar las competiciones cruzadas entre los participantes de numeración inferior y los de numeración superior. En efecto. . El caso básico se da cuando solo hay dos participantes. faltando 2k x2k-1 celdas para completar el calendario total.. El caso recursivo. por ejemplo.N. Si el numero de participantes es 2k ..N. Completemos primero la parte de los participantes de numeración inferior.1. Sin embargo. de numeración comprendida entre 1 y 2k-1 y otro para los participantes comprendidos entre 2k-1 +1 y 2k ..N-1) -> PROCEDURE FormaTabla (IN inf : 1. es más complejo. sucesivamente con los participantes 2k-1 +1..

. medio.. Mezclar (vector.1 := inf ELSE medio := (inf + sup) Div 2. 1. IN inf.1.m y vm+1.N. tabla). medio. La idea consiste en añadir inicialmente a la tabla una columna "ficticia" de índice j=0. Después se genera..N) -> (* ordenación por mezcla *) PROCEDURE OrdenarAux (INOUT Vector : INTEGER1..N. medio. sea vi. OrdenarAux (vector.s un vector de índice inferior i e índice superior s. siendo 1<=k<=n y 0<=l<=(n/2)-1. Ordenación de un Vector por Mezcla: La ordenación de un vector es un problema que se presta fácilmente a la aplicación de la técnica de divide y vencerás. basta con mezclar los dos subvectores. Este proceso de mezcla es realizado por un procedimiento auxiliar. Veamos otra estrategia. medio. medio). la combinación de los dos subvectores ya ordenados es fácil. que almacena los índices de las filas. tabla). sup-1. la mitad izquierda de la tabla. donde se aplica divide y vencerás para resolver el problema y que se aprovecha de la simetría de la solución. N) . Finalmente se completa la mitad derecha de la tabla (correspondiente al cruce de los dos grupos de equipos cuyos subcalendarios se han generado por divide y vencerás).N IF inf = sup-1 THEN tablainf. La partición puede hacerse por la mitad si se toma un índice m=[(i+s)/2] y dos subvectores vi. que obviamente ya esta ordenado.. para obtener un único vector ordenado. mediante divide y vencerás. mediante comparaciones de sus elementos sucesivos. Para el caso general. los componentes tablai.N) -> VAR Medio : 1. FormarTabla (inf. FormarTabla (medio+1. sup. tabla) Este sistema de ecuacionesdefina una función de tiempo del orden de O(n2). también de orden de complejidad cuadrática.. tablasup. sup) OrdenarAux (v.N IF inf < sup THEN medio := (inf+sup) Div 2. de acuerdo con las siguientes expresiones de los índices: i = (k + n/2) Mod (n+1) j = (1 + n/2) Mod n De esta forma se rellenan las casillas aun vacías.. sup).1 : = sup. El caso básico corresponde a un subvector de un solo elemento. tabla). OrdenarAux (vector.l ya completadas. El algoritmo resultante es: PROCEDURE Ordenar (INOUT v : INTEGER1. inf. medio+1. es decir.l)..s . inf. que es mucho mas eficiente que la solución de fuerza bruta. medio+1. CompletarTabla (medio+1. medio. sup : 1. los valores de las casillas (k.medio : 1.. En esta última etapa. sup. CompletarTabla (inf.j a partir de las casillas tablak. inf.sup-1.

b=cte Si n es una potencia de 2. INOUT vector : INTEGER1. es decir. índice : INTEGER i1 := inf. i2 := i2 + 1 j := j + FOR índice IN i1. Es fácil analizar la complejidad del algoritmo para un vector de longitud n. pero mantenga la complejidad asintótica calculada. J := j + 1 FOR índice IN i2.sup DO vectorAuxj := vectorindice ..medio DO vectorAuxj := vectorindice. j := inf. i2. j : INTEGER. Multiplicación de Matrices: Sean dos matrices. a=cte 2T(n/2) + bn.= vectori2. las ecuaciones anteriores se resuelven por sustituciones sucesivas. necesita copiar el vector auxiliar completo en el principal.. de forma que las ecuaciones de recurrencia de la función de tiempo son: T(n) = a. de dimensión nxn. resultando: T(n) = 2T(n/2) + bn= =2K T(n/2K) + kbn = an + bn log2 n El algoritmo de ordenación por mezcla es óptimo en tiempo de ejecución. n =2k para algún k.N) -> VAR vectorAux : INTEGER1. IN sup : INTEGER. La matriz productoC=AxB también es una matriz de nxn cuyo elemento (i.N. n>1. La operación de mezcla es proporcional a n..El procedimiento para realizar la mezcla de los subvectores ordenados es: PROCEDURE Mezclar ( IN inf : INTEGER. J := j + 1 FOR índice In inf. WHILE (i1<=medio) ^ (i2<=sup) DO IF vectori1 << vectori2 THEN vectorAuxj :=vectori1... i1 :=i1 + 1 ELSE vectorAuxj . Los únicos inconvenientes que presenta es que el procedimiento de mezcla necesita gran capacidad de almacenamiento (para dos copias del vector) y que. i2 := medio + 1. i1. IN medio: INTEGER. además de mezclar. A y B. Puede diseñarse un algoritmo de mezcla más complejo que mejore ambos aspectos. n=1.sup DO vectorindice := vectorAuxindice El algoritmo resultante es sencillo conceptualmente.j)-esimo se forma multiplicando cada elemento de la final i-esima de A por el elemento correspondiente de la columna j-esima de B y sumando los productos § .

La resolución de este sistema de ecuaciones nos dice que O(T(n))=OT(n3). La programación dinámica (también llamada planificación dinámica) es una técnica de programación que también permite resolver problemas mediante una secuencia de decisiones. Dos submatrices de (n/2)x(n/2) pueden sumarse en un tiempo bn2. todo problema resoluble con esta técnica debe de satisfacer el principio de optimalidad. Programación Dinámica Principios de programación dinámica Se ha visto que la técnica voraz se aplica a problemas cuya solución puede formularse como el resultado de una secuencia de decisiones. pueden añadirse las filas y columnas de ceros necesarias para formar una dimensión que sea potencia de dos. la técnica de divide y vencerás sugiere un algoritmo distinto. porque la multiplicación esta relacionada con otras operaciones sobre matrices mas usuales. así que el tiempo total del algoritmo de multiplicación es de orden O(n3). que podemos llamar algoritmo convencional de multiplicación de matrices. no se reconsidera en el futuro.parciales. El cálculo de cada elemento Cij requiere n multiplicaciones. que n es una potencia de dos. El algoritmo anterior. El algoritmo de Strassen calcula las cuatro submatrices Cij empleando 7 multiplicaciones y 18 sumas o restas de matrices. Además. asegurando que la secuencia de decisiones es la mejor de las posibles. aunque fuera a costa de un mayor numero de sumas de matrices. Podría conseguirse mas eficiencia si lográramos realizar menos multiplicaciones de matrices. pero de una manera menos directa que en el caso voraz. No es fácil establecer una definición de la programación dinámica. proviene directamente de la definición matemática del producto de matrices. La existencia de un algoritmo eficiente para la multiplicación (en realidad. de forma que no se ha conseguido ningún ahorro sustancial de tiempo. por sencillez.) las submatrices A y B pueden partirse en cuatro submatrices de dimensión (n/2)x(n/2). es decir. para cualquier operación de las anteriores) significaría la existencia de un algoritmo similar para las demás. una característica es que el programa "aprende "dinámicamente de las decisiones que toma. que existe un entero no negativo k tal que n=2k. Este principio establece que "una secuencia óptima de decisiones que resuelve un problema debe cumplir la . interesa encontrar algoritmos mas eficientes. como inversión de una matriz o hallar su determinante. Si el producto AxB tiene la forma: A11 A12 B11 B12 C11 C12 A21 A22 B21 B22 C21 C22 Entonces: C11 = A11*B11 + A12*B21 C12 = A11*B12 + A12*B22 C21 = A21*B11 + A22*B21 C22 = A21*B12 + A22*B22 Para n=2. pero para n>2 las submatrices Cij se calculan mediante multiplicaciones (recursivas) y sumas de submatrices de dimensión (n/2)x(n/2). (Si n no es un potencia de dos. Solamente al final se sabe cuál es la mejor de todas. siendo b alguna constante. Sin embargo. Sin embargo. El método es eficiente porque una vez que se toma una decisión en un paso. los elementos Cij se calculan mediante algunas multiplicaciones y sumas de números. dado que la complejidad respectiva de estas operaciones es O(n3)n y o(n2). Supongamos. no todos los problemas pueden resolverse de esta manera. Sin embargo. La matriz C tiene n2 elementos. Esta vez se necesita producir varias secuencias de decisiones. conduciendo de forma directa a la solución.

1 ) debe expresarse en términos de los valores de decisión existente para decisiones d1 y el subproblema problema ( k+1. Sea D = { v1 . Usando una técnica de fuerza bruta. del gusto del programador. La formulación trasera expresa la decisión de Xi. entonces el problema completo es problema ( l.Xn la secuencia de decisiones necesaria para resolver el problema. El razonamiento anterior se refiere a la primera decisión d1 tomada desde el estado inicial E0 sin embargo. la ecuación de base establece el valor para la etapa n+1 en que no queda ninguna decisión Xi. tal que Eo es el estado inicial del problema y deben tomarse n decisiones d. La ecuación de recurrencia puede formularse de dos formas: delantera o trasera. a partir de la recurrentes con formulación trasera es igual que e la formulación delantera. Además.n ). partiendo como estado inicial de Ek-1. el número de secuencias de decisión es exponencial sobre el número de decisiones. puede generalizarse la formulación del problema a cualquier subsecuencia de decisiones dk . resultará un total de d secuencias posibles de decisión. Podemos formalizar algo más la idea básica. De esta forma se reduce al número total de subsecuencias generadas.) Una solución dinámica para problema ( k. a tomar. sencillamente. a partir de la secuencia de decisiones Xi+1 Xn ( es la clase de formulación adoptada hasta ahora ).. 1<k<n. La expresión inicial de la ecuación de recurrencia. Algoritmos De Vuelta Atrás Existen un alto número de problemas que pueden formularse como la búsqueda de la mejor solución o del conjunto de todas las soluciones que satisfacen ciertas condiciones. 1<i<N1.. que es problema ( n.. la aplicación de la técnica de programación dinámica a un problema significa comprobar primero el principio de optimalidad y desarrollar después unas ecuaciones recurrentes del estilo de (1) y (2).vn} el conjunto de valores de decisión posibles para la decisión d1. además.. En la programación dinámica todos los subproblemas se resuelven de acuerdo con criterio de tamaño creciente y los resultados de subproblemas más pequeños se almacenan en algún tipo de estructura de datos (normalmente tablas) para facilitar la solución de los problemas más grandes. La elección de una formulación delantera o trasera depende del problema considerado o. Tiene sentido centrarse en un subproblema del problema inicial porque éste satisface el principio de optimalidad pero. tiene la ventaja ( quizás paradójica al tratar de un problema más pequeño ) de que proporciona una visión más general del problema en cuestión. 1<i<n .1 ) resultante de aplicar cada valor de decisión. una secuencia óptima de decisiones respecto a E0 es la mejor secuencias de decisión { Vli Sli }. hay un caso en que la decisión d1 no va seguida por ninguna secuencia de decisiones. asimismo. La formulación delantera expresa la decisión de Xl . 1<i<n. Sea X1 . sólo que en orden contrario. Entonces. 1<i<n. La ecuación general relaciona la secuencia óptima en una etapa i con la decisión tomada en la etapa i y la subsecuencia óptima en la etapa posterior i+1. Eli el estado del problema tras la elección del valor vli 1<i<n1 y Sli una secuencia óptima de decisiones respecto al estao Eli.l). Supongamos que tenemos un problema que satisface el principio de optimalidad. si este subproblema de simboliza como problema (k. ¨ ¨¨ ¨ ¨ .propiedad de que cualquier subsecuencia de decisiones también debe ser óptima respecto al subproblema que resuelva ". evitándose una explosión combinatoria en la producción de las secuencias y consiguiéndose soluciones más eficientes en cuanto a tiempo de ejecución.n ). 1<i<n. porque si hay d opciones para cada una de las n decisiones.dl. sea. ( Obsérvese que vamos a usar la técnica de resolución de problemas por generalización para después poder realizar una particularización de la solución obtenida. En resumen.

. Supongamos que existe algún predicado acotador A tal que A(x1... 1. El Algoritmo de Vuelta Atrás se especifica de la forma siguiente: PROCEDURE Retroceso (IN k : INTEGER.. debe existir una función de criterios que debe ser satisfecha por cada secuencia solución u optimizada por dichas secuencias solución si solo queremos la mejor. Por lo tanto.xi) el conjunto de todos los valores posibles de xi+1 tales que (x1. 1.cada solución es el resultado de una secuencia de decisiones. se comprueba si se ha encontrado una solucion.n son aquellos valores generados por G que satisfacen A. Algoritmos Heuristicos Existen muchos problemas para los cuales no se conocen algoritmos que puedan encontrar la solución de forma eficiente: problemas NP-completos. Esquema de Algoritmos de Vuelta Atrás: Sea (x1. Sin embargo... solucion)... En algunos problemas de optimización se conoce un criterio óptimo de selección que puede usarse de forma voraz... los candidatos para la posición i+1 del vector desolucion x1. Después simplemente se llama recursivamente al algoritmo para generar los estados descendientes..n) -> VAR nodo : elemento FOR noso IN G(solucion.xi+1) es falso si el camino (xi. Ramificación (Bifurcacion) Y Acotación Los métodos de Ramificación y Acotación constituyen un a variante de las técnicas de retroceso para problemas donde se trata de encontrar el valor máximo o mínimo de cierta función objeto (esto suele suceder en los problemas de programación lineal entera)... Este mismo proceso se repite en el resto de nodos del árbol. Así. Por supuesto. 1. k) THEN IF R(solucion..... todavía hay otros problemas peores que no queda mas remedio que realizar una búsqueda de la solución. .xi+1) termina en un nodo de respuesta. Sea G(x1. Supongamos que también existe algún predicado R que determina si un camino (x1.xi+1) es un camino hasta el estado del problema. k sirve de cota inferior al retroceso.. y que al seguir avanzando en el árbol (mediante la aplicación de varios pasos de retrocesos) se alcanza un nodo que requiere k+1 colores.k) THEN << guardar µsolucion¶ >>. IF R(solucion.. Otros problemas satisfacen el principio de optimalidad..xi+1) no puede extenderse para alcanzar un nodo de respuesta. Retroceso (k+1.. INOUT solucion : elemento1... El procedimiento no hace ninguna llamada recursiva cuando k = N+1 o cuando ningún nodo generado por G satisface el elemento posible que satisfacen A se añade una solución particular. Se sale del bucle FOR cuando no quedan mas valores para solución terminando la llamada actual al algoritmo. evitando así la exploración de gran parte de al estructura. k-1) DO Solucion k := nodo. En este punto podemos retroceder (y no seguir avanzando por mas ramas). La técnica de ramificación y acotacotacion aplica de la siguiente manera: Supóngase que al recorrer un árbol y alcanza una hoja se tiene una solucion con k colores.. solucion) La llamada inicial del algoritmo es Retroceso(1.. pues tenemos ya una solucion mayor.xi) el camino desde la raíz hasta un nodo de un árbol del espacio de estado. pudiéndose aplicar la técnica de programación dinámica.

. a2. 5. Función de selección: de los nodos candidatos seleccionar el más próximo al último (o al primero) de la secuencia actual (c1. cn).. . Posibilidades: 1. . 5). completo y ponderado G = (V. Solución: (1. 2. Hacer igual que en el algoritmo de Kruskal. (3. A). 2). 1) Coste: 15+20+10+45+50=140 Heurística voraz 2 ± Una solución será un conjunto de aristas (a1. el orden de visita de los nodos. Se hace necesario utilizar algoritmos heurísticos: Un algoritmo heurístico (o simplemente heurística) puede producir una buena solución (puede que la óptima) pero también puede que no produzca ninguna solución o dar una solución no muy buena. ca). an-1) que formen un ciclo hamiltoniano. 3.. Empezando en el nodo 1. Problema de optimización.. 4.. 4. pero necesitamos una solución eficiente. Ejemplo. 3.La solución exacta puede requerir un orden factorial o exponencial: el problema de la explosión combinatoria. (1. sin importar el orden.. 3). encontrar un ciclo simple de costo mínimo que pase por todos los nodos. 2) Coste: 30+15+25+10+45=125 Empezando en el nodo 3. c2.. 2. Solución: (5. Es un problema NP. Factible: una arista se puede añadir a la solución actual si no se forma un ciclo (excepto para la última arista añadida) y si los nodos unidos no tienen grado mayor que 2. Empezar con un grafo sin aristas. Las aristas son los candidatos. . (1. Selección: seleccionar la arista candidata de menor coste. pero garantizando que se forme un ciclo. El problema del viajante Problema: Dado un grafo no dirigido. Normalmente. La estructura de algoritmo voraz se puede utilizar para construir procedimientos heurísticos: hablamos de heurísticas voraces. (4.. En cada paso moverse al nodo no visitado más próximo al último nodo seleccionado. Objetivo: obtener buenas soluciones en un tiempo de ejecución corto. 4). donde la solución está formada por un grupo de elementos en cierto orden: podemos aplicar el esquema voraz. c2. Los nodos son los candidatos.. se basa en un conocimiento intuitivo del programador sobre un determinado problema. Heurística voraz 1 ± Una solución será un cierto orden en el conjunto de nodos (c1. Inicialización: seleccionar un nodo cualquiera. ‡Ejemplo. 5)) Coste = 10+15+20+45+50 = 140 . Acabamos cuando tengamos n nodos. Empezar en un nodo cualquiera. Solución: ((2.

En consecuencia. seria necesario demostrar que el conjunto de todos los vértices inciden a las aristas de un ajuste maximal M para un grafo G es un recubrimiento con no mas de dos veces el numero de veces el recubrimiento de tamaño mínimo.Conclusiones: Ninguno de los dos algoritmos garantiza una solución óptima. Algoritmos De Aproximación Dado un problema NP completo. como es calcular el ajuste maximizal del grafo G. a partir de la solución del algoritmo intentar hacer modificaciones locales para mejorar esa solución. ó bien. es probable que no sepamos resolverlo de manera precisa y completa utilizando un algoritmo polimico en tiempo. Este problema se puede resolver a través de otro aproximado. próximas a la óptima. Sin embargo. Posibles mejoras: buscar heurísticas mejores. A continuación se ilustra este tipo de tratamiento de problemas al problema de recubrimiento de un grafico: Dado un grafo G=(V. los algoritmos que no conducen a una solución óptima se llaman algoritmos de aproximación. Esto es evidente. los vértices incidentes a las aristas de M son un recubrimiento de G. normalmente ambos dan soluciones buenas. Se trata de calcular un subconjunto A¶ de aristas tal que dos aristas cualquiera de A¶ no tengan ningún vértice común y toda arista de A-A¶ comparta algún vértice común con una arista de A¶.A). resulta parcialmente interesante que estos garanticen una cota en el margen de imprecisión. repetir la heurística 1 con varios orígenes. ningún vértice perteneciente a M puede recubrir a mas de una arista en M. Este nuevo problema garantiza conseguir un recubrimiento que contiene no más de dos vértices del recubrimiento mínimo. de una en una y en cualquier orden e ir eliminando las incidentes al conjunto que se esta construyendo hasta recubrir todo en grafo. se trata de encontrar un conjunto con el menor numero de vértices tal que toda arista sea incidente por lo menos de un vértice de V. Para este tipo de problemas. . por lo menos la mitad de los vértices de M deben pertenecer a un recubrimiento. también por la propia definición. ya que por la definición de ajuste maximal. El procedimiento para construir un ajuste maximizal de un grafo G consistiría en ir tomando aristas de G. Sin embargo. Para poder aplicar el nuevo problema aproximado.

Sign up to vote on this title
UsefulNot useful