Tema 3 Algoritmos Voraces. Introducción - Conjunto de algoritmos que toman decisiones basándose en la información disponible inmediatamente. - Sin tener.

Slides:



Advertisements
Presentaciones similares
Capítulo 2 Algoritmos.
Advertisements

Diseño y análisis de algoritmos
Diseño y análisis de algoritmos
Diseño y análisis de algoritmos
Árboles Grafo que no contiene ciclos, es decir es un grafo también acíclico, pero a su vez es conexo.
GRAFOS: ALGORITMOS FUNDAMENTALES
Investigación de Operaciones
OPTIMIZACIÓN EN REDES EN ALGUNOS PROBLEMAS DE OPTIMIZACIÓN PUEDE SER ÚTIL REPRESENTAR EL PROBLEMA A TRAVÉS DE UNA GRÁFICA: ruteo de vehículos, distribución.
MATEMÁTICAS DISCRETAS.
Instituto Tecnológico De Villahermosa
Investigación de Operaciones II
Investigación de Operaciones II
Unidad 4: Análisis de algoritmos (parte II)
Método de Ford-Fulkerson
Investigación Operativa

2- SIMPLEX.
Analisis y Diseño de Algoritmos Tema: Grafos 3ra Parte
Problemes de Viatjants
AED I. Estructuras de Datos.
GRAFOS HUGO ARAYA CARRASCO.
Teoría de Grafos.
PROGRAMACIÓN PARALELA EN ALGORITMOS SOBRE GRAFOS
Modelos Cuantitativos
Grafos. Un Grafo G es un par de conjuntos (V, E), donde V es un conjunto no vacío de elementos llamados vértices o nodos y E es un conjunto formado por.
Teoria de grafos.-clase 4
Árboles, montículos y grafos Cola de prioridades, montículos
EL PODER DE SOLVER.
Universidad de los Andes-CODENSA
Árbol recubridor mínimo Distancias
I n s t i t u t o T e c n o l ó g i c o d e T e c n o l ó g i c o d e V i l l a h e r m o s a ING. EN SISTEMAS CATEDRATICO: I.I. Zinath Javier Gerónimo.
Ejemplo de aplicación de las ANN
Single-Source Shortest Paths “Camino más corto desde/hacia una fuente”
Problemas de Decisión y Optimización
Matemáticas Discretas
Diseño y análisis de algoritmos
Diseño y análisis de algoritmos

ALGORITMOS APROXIMADOS
DEFINICIONES Sea (P) el siguiente problema de programación lineal:
Diseño y análisis de algoritmos
Parte II. Algorítmica. 3. Algoritmos voraces.
Diseño y análisis de algoritmos
Divide y vencerás 1. Método general.
Surge cuando se necesita un modelo costo-efectividad que permita transportar ciertos bienes desde un lugar de origen a un destino que necesita aquellos.
INSTITUTO TECNOLÓGICO DE VILLAHERMOSA. CATEDRATICO:
Capítulo 7 Gestión de memoria.
Backtracking 1. Método general. 2. Análisis de tiempos de ejecución.
Parte I. Estructuras de Datos.
Agustín J. González ELO320: Estructura de Datos y Algoritmos
Parte II. Algorítmica. 5. Backtracking. 1. Análisis de algoritmos.
Parte I. Estructuras de Datos.
Tema 11: Programación dinámica
Parte I. Estructuras de Datos.
Sabemos reconocerlas, y calcularlas como soluciones de sistemas de ecuaciones, o de desigualdades Buscamos métodos de cálculo generales y eficientes Problemas.
Tema 10: Algoritmos voraces
1 Flujo Máximo Agustín J. González ELO320: Estructura de Datos y Algoritmos.
Agustín J. González ELO320: Estructura de Datos y Algoritmos
Arboles B (búsqueda externa)
TEMA 5: El problema del flujo con costo mínimo
Estructura de Datos 4 Grafos Dirigidos
Instituto Tecnológico De Villahermosa Alumno: Lázaro García Hernández.
UNIDAD 2 Grafos Árboles abarcadores mínimos Caminos más cortos.
ARBOLES GENERALIZADOS
Introducción a los TADs
Capítulo 8: Árboles Autor: José Alfredo Jiménez Murillo.
Matemáticas Discretas MISTI
Recorridos de grafos Segunda Parte M.C. Meliza Contreras González.
Hernández Camacho Víctor Jesus Islas Sánchez Karla Vanessa
Algoritmos voraces Códigos de Huffman. Descripción del problema Tenemos un archivo de entrada. Asumiremos que el archivo está compuesto de bytes (enteros.
Transcripción de la presentación:

Tema 3 Algoritmos Voraces

Introducción - Conjunto de algoritmos que toman decisiones basándose en la información disponible inmediatamente. - Sin tener en cuenta los efectos de las decisiones en el futuro. - Fáciles de diseñar, implementar y, en muchos casos, eficientes si funcionan. - Se utilizan para resolver problemas de optimización.

Ejemplo  Devolver el cambio en la siguiente situación.  Devolver una cantidad a un cliente utilizando el menor número de monedas.  Monedas posibles: 500, 200, 100, 25, 10, 5 y 1  Para devolver 289:  1 de 200 (200)  3 de 25 (275)  1 de 10 (285)  4 de 1 (289)  Total 9 monedas

Algoritmo voraz Escoger cada vez una moneda del mayor valor sin que la suma supere la cantidad total a devolver. Es el método aplicado inconscientemente para este caso, en la vida diaria. Otra veces lo que se intenta es eliminar la calderilla.

función devolver(n):conjunto de monedas const c={500,200,100,25,10,5,1} S=0 //conjunto solución s=0 //suma de los elementos de S mientras s  n hacer x=mayor elemento de C tal que s+x  n si no existe x, devolver “No hay solución” S=S U {una moneda de valor x} s=s+x devolver S Si no hay suficientes monedas de algún tipo seleccionado, el algorit- mo NO funciona ALGORITMO INFORMAL

Características del algoritmo Este algoritmo, teniendo monedas suficientes de cada tipo (si no es así no funciona), produce una solución óptima. Aunque esta afirmación es difícil de probar. Es voraz  En cada paso selecciona la mayor de las monedas, sin pensar en las consecuencias posteriores. Es decir no le preocupa lo correcto de la decisión. Nunca modifica la decisión una vez ha escogido una moneda, y una vez incluida en la solución siempre estará ahí.

Nota Existe un algoritmo alternativo para el problema de “Devolver Cambio” que emplea programación dinámica. Éste siempre funciona, mientras que el voraz puede fallar, pero es menos comprensible y menos eficiente.

ELEMENTOS CARACTERISTICOS DE LOS ALGORITMOS VORACES Conjunto de candidatos  Dará lugar a candidatos seleccionados y candidatos rechazados. Función solución  Comprueba si el conjunto de candidatos seleccionados es ya una solución, sea o no óptima. ¿suman las monedas seleccionadas n? Si  Fin Función de factibilidad  Comprueba si el conjunto de candidatos seleccionados es factible (si es posible completar la solución).

ELEMENTOS CARACTERISTICOS DE LOS ALGORITMOS VORACES ¿se supera la cantidad n? Si es así, el candidato no es factible y no se selecciona en caso contrario si. Función de selección  Candidato más prometedor de los no seleccionados. Función objetivo  Devuelve la solución al problema planteado.

CARACTERÍSTICAS GENERALES Búsqueda de un conjunto de candidatos que sean solución óptima al problema planteado. Ejemplos: Ruta más corta entre dos nodos. D evolver cambio con menor número de monedas. Avanzan paso a paso: inicialmente el conjunto de candidatos está vacío. En cada paso se considera añadir el mejor candidato, según la función de selección.

CARACTERÍSTICAS GENERALES Si con el nuevo candidato no es factible, se rechaza, en otro caso se escoge para siempre y se introduce en el conjunto de candidatos seleccionados. Cada vez que se añade un candidato, se comprueba si es solución. Si funciona bien, la primera solución encontrada es la óptima.

NOTAS La función de selección suele estar relacionada con la función objetivo. –Si se quiere maximizar beneficios  escoger el candidato con mayor valor individual. –Si se quiere minimizar costes  selección del candidato más barato. Pueden definirse varias funciones de selección, se escoge la más adecuada en función de los objetivos.

Caso general función voraz(C:conjunto):conjunto S=  //S solución y C conjunto de candidatos mientras C  y no solución(S) hacer x=seleccionar c que optimice la f. selección C = C - {x} si factible(S  {x}) entonces S=S  {x} si solución(S) entonces devolver S sino devolver “No hay solución” ALGORITMO FORMAL

Aplicación al ejemplo Devolver Cambio Adecuación de las características generales de los algoritmos voraces al problema de devolver cambio. Candidatos: Conjunto de monedas {500, 200, 100, 25, 10, 5, 1} con tantas monedas de cada valor que nunca las agotaremos. Función solución: Comprueba si el valor de las monedas seleccionadas es el valor que hay que devolver exactamente.

Aplicación al ejemplo Devolver Cambio Conjunto de monedas será factible si su valor total no sobrepasa la cantidad a pagar. Función de selección: Toma la moneda con valor más alto que quede en el conjunto de candidatos. Función objetivo: Cuenta el número de monedas de la solución obtenida.

Grafos: árboles de recubrimiento mínimo Aplicación del método voraz a la teoría de grafos. G= Grafo conexo no dirigido. Todos los nodos están conectados por algún camino y si existe la arita (u,v) también existe la arista (v,u). Cada arista tiene un costo ( o longitud)  0. Nota: Un grafo conexo de recubrimiento deriva en un árbol; si no es conexo en varios árboles. N: Nodos A: Aristas

Problema 1 Hallar un subconjunto T de las aristas de G tal que las aristas de T conecten a todos los nodos y la suma de las longitudes de las aristas de T sea tan pequeño como sea posible. Como G es conexo  al menos  una solución Si existen aristas de longitud 0   varias soluciones con la misma longitud. Entonces escoger la que tenga un menor número de aristas.

Problema 2 Hallar un subconjunto T de las aristas de G cuyo coste total sea mínimo. Igual que el anterior: coste=longitud Se obtiene un nuevo grafo  G’= donde N es el conjunto de nodos y T el de aristas del grafo solución

Conceptos básicos para el grafo solución Un grafo conexo con n nodos tiene al menos n-1 aristas. Un grafo conexo con n nodos y más de n-1 aristas tiene al menos un ciclo. Si el grafo solución G’ es conexo y T tiene más de n-1 aristas   al menos un ciclo y se puede eliminar al menos una arista sin desconectar G’. Esa arista debe formar parte de un ciclo, con lo que la eliminación:

Conceptos básicos para el grafo solución Puede disminuir la longitud de las aristas de T o no (si es 0). Disminuye número de aristas en T. Disminuye la suma de longitudes, si la arista tiene longitud distinta de 0. Esta nueva solución es mejor, por tanto 

Para la solución T debe tener exactamente n-1 aristas, y como G’ es conexo  es un árbol (grafo acíclico, conexo y no dirigido) G’ es el Árbol de Recubrimiento Mínimo de G

Aplicaciones de este problema Tendido de líneas eléctricas entre ciudades  G’ la red más barata posible para dar servicio a todas las ciudades, siempre que sólo se puedan usar conexiones directas entre las mismas. Trazado de carreteras entre pueblos con mínimas distancias.

Algoritmo voraz para resolver este problema: Táctica A: Comenzar con T vacío, y en cada etapa seleccionar la arista más corta que no se haya seleccionado o rechazado, independientemente de donde se encuentre  Planteamiento Kruskal Táctica B: Seleccionar un nodo y construir un árbol a partir de él, seleccionando en cada etapa la arista más corta posible hasta otro nodo, extendiendo el árbol  Planteamiento Prim

Correspondencia de este problema con los elementos de los algoritmos voraces: Conjunto de candidatos: Aristas de G, es decir A. Función solución: Un conjunto de aristas es solución si constituye un árbol de recubrimiento para los nodos de N

Correspondencia algoritmos voraces:  Función de factibilidad: Un conjunto de aristas es factible si no contiene ciclos.  Función de selección: Varía según el algoritmo (Arista más corta, etc..).  Función objetivo: Minimizar la longitud total de las aristas de la solución

Algoritmo de Kruskal Inicialmente tenemos: T=conjunto de aristas solución, vacío al comienzo y cada nodo de G forma una componente conexa distinta Los nodos de una componente conexa en T forman un árbol de recubrimiento mínimo para los nodos de esa componente, y cada nodo sólo debe aparecer en una componente conexa. Al final solo habrá una componente conexa en T, luego T es un árbol de recubrimiento mínimo para todos los nodos de G.

Proceso del algoritmo de Kruskal: 1. Ordenar las aristas de G por orden creciente de longitud (coste). 2. Tomar la arista de longitud menor que no se haya seleccionado o rechazado. 3. Si una arista une a dos nodos de componentes conexas distintas, la arista se añade a T, uniendo las componentes en una sola. 4. En caso contrario( la arista une dos nodos de una misma componente conexa), se rechaza la arista (si se añadiera  ciclo). 5. Volver al paso 2 hasta que sólo quede una componente conexa en T

Ejemplo Longitud de la arista

Aristas por orden creciente de longitud : {1,2} {2,3} {4,5} {6,7} {1,4} {2,5} {4,7} {3,5} {2,4} {3,6} {5,7} {5,6} Nº paso Ar.considerada Comp. conexas Inicialmente {1} {2} {3} {4} {5} {6} {7} 1 {1,2}  T {1,2} {3} {4} {5} {6} {7} 2 {2,3}  T {1,2,3} {4} {5} {6} {7} 3 {4,5}  T{1,2,3} {4,5} {6} {7} 4 {6,7}  T{1,2,3} {4,5} {6,7} 5 {1,4}  T{1,2,3,4,5} {6,7} 6 {2,5} Rechazada, ¿forma un ciclo? 7 {4,7}  T{1,2,3,4,5,6,7}

Al final T = {{1,2},{2,3},{4,5},{6,7},{1,4},{4,7}} El árbol de recubrimiento mínimo está formado por las aristas de T (longitud 17= )

Teorema: El algoritmo de Kruskal halla un árbol de recubrimiento mínimo (Demostración en la página 219 de Brassard) Implementación: –  Operaciones básicas sobre conjuntos (cada componente conexa) –  buscar(x): indica la componente conexa a la que  el nodo x –  fusionar(A,B): une las componentes conexas A y B Representación del grafo: vector de aristas con sus longitudes asociadas (matriz cuyos índices sean los nodos)

Funcion Kruskal(G= :grafo,long A  R + ):cjto arist Ordenar A por longitudes crecientes a=n(n-1)/2 máximo n=nº de nodos en N T=  //contendrá las aristas del árbol de rec. mínimo Iniciar n conjuntos, cada uno es un elemento de N Repetir e = {u,v}//aris de long. más corta no selecc. ni rech comp_u = buscar{u} comp_v = buscar{v} si comp_u  comp_v entonces fusionar(comp_u,comp_v) //T=T  {e} // si no T=T  {e} Hasta que T contenga n-1 aristas // o una sola comp conex Devolver T

Tiempo de ejecución del algoritmo de Kruskal: n  número de nodos a  nº de aristas Ordenación de aristas  (a log a)  (a log n) Iniciar los n conjuntos disjuntos  (n) Nº de operaciones buscar es 2a como máximo Nº de operaciones fusionar es n-1 como máximo Resto de operaciones  (a) (en peor caso) Luego Kruskal  (a log n) La complejidad admitida es:  si el grafo es disperso:  (n log n)  si el grafo es denso:  (n 2 log n)

Procedure Kruskal(var grafo:array[1..n2] of Aristas); Var: Padre:array[1..n] of integer; Soluc:array[1..n,1..2] of integer; CostArbMin:real; RaizOr,RaizEx,k,i:intege { {ordenar grafo según la clave Valor de menor a mayor} for i:=1 to n do Padre[i]:=-1; k:=0; i:=0; CostArbMin:=0;

while (k<n-1) and (grafo[i+1].valor<  ) do { i:=i+1; with grafo[i] do { BuscaArbol(Or,RaizOr); BuscaArbol(Ex,RaizEx); if RaizOr  RaizEx then { k:=k+1; CostArbMin:=CostArbMin + Valor; Soluc[k,1]:=Or; Soluc[k,2]:=Ex; UnirArbol(RaizOr, RaizEx); } }

Procedure BuscaArbol(Nodo:integer; var RaizArbol:integer); Var j:integer; { j:=Nodo while Padre[j]>0 do j:=Padre[j]; RaizArbol:=j; while Nodo  RaizArbol do { j:=Padre[Nodo]; Padre[Nodo]:=RaizArbol; Nodo:=j; } }

Procedure UnirArbol(RaizArbol1,RaizArbol2:intger); Var Sum:integer; { Sum:=Padre[RaizArbol1]+Padre[RaizArbol2]; if Padre[RaizArbol1] > Padre[RaizArbol2] then { Padre[RaizArbol1]:=RaizArbol2; Padre[RaizArbol2]:=Sum; } else { Padre[RaizArbol2]:=RaizArbol1; Padre[RaizArbol1]:=Sum; } }

Precisiones al algoritmo de Kruskal: Declaración de Aristas type Aristas=record valor:real; Or,Ex:integer; end; El array Soluc de tamaño n·2 irá conteniendo la solución: Soluc[1..n][1..2] (Soluc[i][1]: nodo OR, Soluc[i][2]:nodo Ex) El array Padre[1..n]: Padre[i]=nodo antecesor del nodo i Si Padre[i]<0  i es la raíz y contiene el nº de nodos de ese árbol o componente conexa Const n 2 = n·n

Padre  Inicio  k=0; i=0; costArbMin=0; n=

Complejidad: Ordenar grafo: ordenar un array de tamaño 1..a (a=n·n) Como queremos ordenar todas las aristas del grafo según su valor, el orden de complejidad de esta ordenación es: O(alog a)  n-1<a<n(n-1)/2  O(n 2 log n 2 )  O(n 2 log n) Inicializar  O(n)

Complejidad While: Interior: UnirArbol  O(1) BuscaArbol  O(n) Resto  O(1) Nº de vueltas  Depende de lo equilibrado que estén los subárboles que se van generando: * caso peor: n vueltas (extendido) * caso mejor: log n vueltas (equilibrado) Por tanto: O(n 2 ) c.peor o O(nlog n) c.mejor La complejidad se puede obtener en función de las aristas (a) o de los nodos (n) como tamaño del problema, sabiendo que a=n 2

Algoritmo de Prim El árbol crece desde una raíz arbitraria, en cada fase se añade una rama al árbol ya construido, hasta conectar con él todos los nodos. G=  N ( nodos ) A( aristas ) B:cjto de nodos  inicio, un solo nodo T:cjto de aristas solución  inicio, vacío

Algoritmo de Prim Funcion PRIM(G= :grafo; longitud A  R + ):cjto aristas T=  ; B={nodo arbitrario de N} Mientras B  N buscar {u,v} de longitud mínima tal que u  B y v  N-B T = T  {u,v} B = B  {v} Devolver T

Partiendo de cualquier nodo se obtendrán las mismas aristas Teorema: El algoritmo de Prim halla un árbol de recubrimiento mínimo (es decir, es una solución óptima) Demostración en página 221 Brassard

Elementos característicos en A.Voraces Candidatos  Aristas Función de factibilidad: El conjunto T es factible si no tiene ciclos. Función objetivo: Minimizar la longitud total de las aristas solución. Función solución: Conjunto de aristas que constituyen un árbol de rec.mínimo para los nodos de N. Función de selección: arista más corta.

Tomando como nodo inicial el Utilizando el algoritmo de Prim, encontrar el árbol de recubrimiento mínimo

No se ordenan las aristas. En total tenemos las siguientes: {1,2} {2,3} {4,5} {6,7} {1,4} {2,5} {1,7} {3,5} {2,4} {3,6} {5,7} {5,6} PasoAristasConjunto B Inicio {1} 1 {1,2} {1,2} 2 {2,3} {1,2,3} 3 {1,4} {1,2,3,4} 4 {4,5} {1,2,3,4,5} 5 {4,7} {1,2,3,4,5,7} 6 {7,6} {1,2,3,4,5,6,7} Al final =17

Implementación de Prim N={1,2,...,n} L: matriz que da la longitud de todas las aristas de modo que: –L(i,j)>0 indica que hay una arista de i a j –L(i,j)= , no hay arista. Matriz mas_proximo[i] : indica el nodo de B más próximo a i Matriz distmin[i]: distancia desde i hasta el nodo más próximo calculado en mas_proximo distmin[i]=-1  i  B, sirve para indicar si un nodo está o no en B

Funcion Prim(L[1..n,1..n]):conjunto de aristas T=  ; Para i=2 hasta n { mas_proximo[i]=1; distmin[i]=L[i,1]; } Repetir n-1 veces { min=  ; Para j=2 hasta n { Si 0  distmin[j]<min entonces { min=distmin[j]; k=j; } } T=TU{mas_proximo[k],k}; distmin[k]=-1 Para j=2 hasta n { Si L[j,k]<distmin[j] entonces { distmin[j]=L[j,k]; mas_proximo[j]=k; } } } Devolver T

Complejidad Primer para  O(n) Segundo para  O(n) Tercer para  O(n) Repetir n-1 veces que engloba a los dos últimos para  O(n 2 ) Por tanto Prim  (n 2 ) Kruskal: –Si el grafo es denso   (n 2 lg n) –Si el grafo es disperso   (n lg n)

Grafos: caminos mínimos G= Grafo dirigido, con longitud de las aristas mayor o igual a cero. Encontrar el camino mínimo: Algoritmo voraz  Algoritmo de Dijkstra S: Conjunto con los nodos seleccionados (Se conoce la distancia mínima a estos nodos) C: Conjunto con el resto de nodos (no se conoce la distancia mínima desde el origen hasta esos nodos) N=S  C, en cada paso selecciona el nodo de C cuya distancia desde el origen sea mínima. Menor longitud Menor coste Ruta más barata

DEFINICIONES Camino especial, desde el origen a un nodo, es cuando todos los nodos intermedios pertenecen a S. Existe una matriz D con la longitud del camino especial más corto que va a cada nodo, desde el origen. En cada fase se añade un nuevo nodo v a S, de forma que el camino especial más corto hasta v es también el más corto de los caminos hasta v.

....DEFINICIONES Todos los caminos desde el origen hasta algún otro nodo son especiales. Los valores de D dan la solución del problema de caminos mínimos. La matriz L contiene las longitudes de todas las aristas dirigidas: L[i,j]  0 si la arista (i,j)  A L[i,j]=  No  arista

Funcion Dijkstra(L[1..n,1..n]):matriz[2..n] D: matriz[2..n] C=2,3,...,n {S=N-C} // S={1} Para i=2 hasta n { D[i]=L[1,i] ; } Repetir n-2 veces { v=algún elemento de C que minimice D[v] C = C – {v} ; S = S U {v} Para cada w  C D[w] = min(D[w], D[v]+L[v,w]) } Devolver D

Para poder determinar los caminos mínimos y por dónde pasa ese camino. Se define P[2..n] tal que P[v] indica el número de nodos que preceden a v en el camino más corto. Modificar el algoritmo (contenido del para) Si D[w]>D[v]+L[v,w] entonces { D[w] = D[v] + L[v,w] P[w] = v }

Teorema El algoritmo de Dijkstra halla los caminos más cortos desde un único origen hasta los demás nodos Demostración en la página 225 de Brassard Análisis del algoritmo de Dijkstra: - Inicialización  O(n) - Repeat  (n 2 ) - Para interno  O(n) Por tanto es  (n 2 )

Elementos de los algoritmos voraces: Candidatos: Nodo origen y el resto de nodos F. Factibilidad: El nuevo candidato es siempre factible si D[candidato] es la mínima F. objetivo: Caminos mínimos con las distancias mínimas del origen a cada nodo F. Solución: no se realiza F. Selección: selecciona el nodo con mínima distancia conocida al origen Dijkstra no obtiene la solución óptima si se permiten valores negativos en las distancias No obtiene soluciones óptimas para caminos máximos

Ejemplo de aplicación de la función de dijkstra para calcular el camino mínimo

PasoVCD[2, 3, 4, 5] P Inici ---- {2,3,4,5} [50, 30, 100, 10]P[5]=1 1 5 {2,3,4} [50, 30, 20, 10] P[4]=5 2 4 {2,3} [40, 30, 20, 10] P[2]=4 3 3 {2} [35, 30, 20, 10] P[2]=3 Aunque se realizará otra iteración más, D no cambiaría P[2]= 3P[3]=1P[4]=5P[5]=1

Solución

El problema de la mochila Tenemos una mochila y n objetos i=1,2,...,n El obj. i tiene un peso positivo w i y un valor v i La mochila soporta un peso máximo W Objetivo: Llenar la mochila maximizando el valor de los objetos transportados en ella. Se pueden descomponer los objetos en trozos más pequeños. Fracción x i del objeto i, 0  x i  1 para 1  i  n. Problema: maximizar  x i v i de modo que  x i w i  W. Cumpliendo v i >0 w i >0 y 0  x i  1,  1  i  n

Elementos Candidatos: Objetos a introducir. F. Solución: Vector(x 1,...,x n ) indicando la fracción de objeto que se incluye. F. Factibilidad: Es factible si se respetan las restricciones. F. Objetivo: Valor total de los objetos en la mochila. F. Selección: Seleccionar el objeto con mayor valor, tomando la mayor fracción posible del objeto.

Funcion mochila(w[1..n],v[1..n]):x[1..n] Para i=1 hasta n hacer x[i]=0 Mientras peso<W hacer i=el mejor objeto no seleccionado si peso+w[i]<=W entonces x[i]=1 peso=peso+w[i] sino x[i]=(W-peso)/w[i] peso=W Devolver x Función Mochila

Funciones de selección posibles Objeto más valioso: Incrementa el valor de la carga rápidamente. Objeto de menor peso: La capacidad se agota lentamente. Objeto cuyo valor por unidad de peso sea el mayor posible. Ejemplo: Como llenar una mochila de capacidad 100 con 5 objetos de valores (20, 30, 66, 40, 60) y pesos (10, 20, 30, 40, 50) con cada una de las tres tácticas.

Obj. 1Obj. 2Obj. 3Obj. 4Obj. 5 Valor V i Peso W i Relación V i /W i

Solución Sel.12345Valor Final Mochila Máx V i 1º3º ½ 2º66+60+(1/2)40=146 [0, 0, 1, ½, 1] Min W i 1º2º3º4º =156 [1, 1, 1, 1, 0] Máx V i /W i 2º3º1º4º 4/ (4/5)60=164 [1, 1, 1, 0, 4/5] ÓPTIMO

Teorema: Si seleccionamos los objetos por orden decreciente de v i /w i, y se permite dividirlos, el algoritmo de la mochila encuentra una solución óptima (Dem. página 230 de Brassard) Complejidad: Si están ordenados (creciente de v i /w i ):  O(n) Incluyendo ordenación:  O(n lg n) El problema de la mochila no se resuelve de manera óptima con Devorador, al no dejar que los los objetos se dividan. En este caso, sí se obtiene una solución óptima con Programación Dinámica.