Método codicioso de algoritmos

El método codicioso consiste en descomponer un problema complejo en una serie de opciones óptimas locales relativamente simples.Cada paso de la elección es una extensión de la solución actual hasta que se obtiene la solución completa del problema. La aplicación típica del método codicioso es resolver problemas de optimización, y para muchos problemas, se puede obtener la solución óptima general.Incluso si no se puede obtener la solución óptima general, suele ser una buena aproximación de la solución óptima.

Visión general

Ideas de diseño del método codicioso

El método codicioso es miope y no considera la optimalidad general. La elección que hace es solo un óptimo local en cierto sentido. Esta elección óptima local no siempre logra la solución óptima general, pero generalmente puede obtener una aproximación Óptima solución.

El problema resuelto por el método codicioso generalmente tiene dos propiedades más importantes: la propiedad de subestructura óptima y la propiedad de elección codiciosa.

1) La propiedad de subestructura óptima: Cuando la solución óptima de un problema incluye la solución óptima de sus subproblemas, se dice que el problema tiene la propiedad de subestructura óptima. También se dice que el problema satisface el principio de optimalidad, y la subestructura óptima del problema La naturaleza estructural es la característica clave de que el problema puede resolverse mediante el método de programación dinámica o el método codicioso.

2) La naturaleza de la elección codiciosa: la denominada naturaleza de la elección codiciosa significa que la solución óptima general del problema se puede obtener a través de una serie de elecciones óptimas locales, es decir, elecciones codiciosas. El método codicioso generalmente toma una serie de elecciones codiciosas de arriba hacia abajo. Determinar si hay una elección codiciosa

  • Por lo general, primero examine una solución óptima general del problema y demuestre que esta solución óptima se puede modificar para que comience a partir de una elección codiciosa.
  • Después de hacer una elección codiciosa, el problema original se reduce a un subproblema similar en una escala más pequeña.
  • Utilice la inducción matemática para demostrar que a través de cada paso de una selección codiciosa, finalmente se puede obtener la solución óptima general del problema.

Proceso de resolución del método codicioso.

El método codicioso se suele utilizar para resolver el problema de optimización, partiendo de un cierto estado inicial, de acuerdo con la estrategia local óptima actual, satisfaciendo la ecuación de restricción como condición, tomando como criterio la función objetivo para crecer más rápido (más lento), en el conjunto de candidatos Haga una serie de elecciones para formar una solución factible al problema lo antes posible.

Método codicioso en problema gráfico

Problema de TSP

El problema TSP se refiere a un viajero que quiere viajar n ciudades, requiere que cada ciudad experimente y solo experimente una vez, y luego regresa a la ciudad de salida y requiere la distancia más corta.

Hay dos estrategias codiciosas para resolver problemas de TSP mediante un método codicioso

  1. Estrategia del vecino más cercano: partiendo del vértice, cada vez que se selecciona el vecino y la distancia es la más corta. El resultado final de este programa es difícil de garantizar, así que pase.

  2. Estrategia de enlace más corto: cada vez que se selecciona el borde más corto para agregarlo al conjunto de soluciones dentro del rango de todo el gráfico, pero es necesario asegurarse de que los bordes agregados al conjunto de soluciones eventualmente formen un bucle hamiltoniano. Por lo tanto, cuando se selecciona una arista (u, v) del conjunto de aristas restante E 'para agregarla al conjunto de solución S, se deben cumplir las siguientes condiciones:

    • La arista (u, v) es la arista con el menor costo en el conjunto de aristas E '
    • Después de agregar la arista (u, v) al conjunto de solución S, no se generará ningún bucle en S
    • Después de que se agrega la arista (u, v) al conjunto de solución S, S no produce ramas

    Esta idea puede resolver el problema de TSP, obtener el borde más corto y usar la clasificación de montones, determinar si dos vértices están conectados y si hay ramas, y usar la búsqueda de unión para mejorar el rendimiento del tiempo hasta O (nlog2 n)

No hay un tema relacionado con el problema de TSP, por lo que no lo haré aquí, pero esta idea es en realidad más fácil que la programación dinámica, pero es mucho más difícil en la implementación específica.

Problema de coloración de gráficos

Dado un gráfico conectado no dirigido G = (V, E), encuentre el número de color mínimo k del gráfico G, de modo que se usen k colores para colorear los vértices en G, de modo que dos vértices adyacentes cualesquiera se puedan colorear de manera diferente.

La estrategia codiciosa es: elegir un color, tomar cualquier vértice como vértice inicial e inspeccionar cada vértice en el gráfico que no está coloreado a su vez. Si un vértice se puede colorear con el color 1, en otras palabras, los puntos adyacentes del el vértice aún no ha sido coloreado, luego use el color 1 para colorear el vértice. Cuando no haya ningún vértice que pueda ser coloreado con este color, seleccione el color 2 y un vértice sin colorear como el vértice inicial, y use el segundo color para colorear tantos vértices como sea posible. Si hay vértices sin colorear, elija el color 3 y coloree tantos vértices como sea posible, y así sucesivamente.

Esta estrategia tiene mucho que ver con el orden en que se seleccionan los vértices para colorear, y es difícil confirmar que sea la solución óptima, no sé por qué el autor habla de este problema.

Problema mínimo del árbol de expansión

Sea G = (V, E) un gráfico conectado no dirigido, y la suma de los pesos de cada borde en el árbol de expansión se denomina costo del árbol de expansión. Entre todos los árboles de expansión de G, el árbol de expansión con el costo más pequeño se llama árbol de generación mínima.

  1. Estrategia de vértice más cercano: seleccione un vértice, encuentre el vértice más cercano adyacente al vértice, después de agregar el punto, encuentre el vértice más cercano adyacente a estos dos vértices y repita el proceso hasta que se agreguen todos los vértices. Esto también se denomina algoritmo Prim y su complejidad de tiempo es O (n ^ 2).
  2. Estrategia de borde más corto: La estrategia de borde más corto comienza desde TE = {}. Cada elección codiciosa es seleccionar el borde más corto (u, v) del conjunto de bordes E. Si el borde (u, v) se agrega al conjunto TE sin generar un bucle, luego agregue el borde (u, v) al conjunto de bordes TE y elimínelo del conjunto E. Esto también se denomina algoritmo de Kruska y su complejidad temporal es O (elog2 e).

    La prueba de estos dos algoritmos se puede probar por contradicción: si no es óptimo, significa que la distancia de un punto a los otros puntos es menor que el borde actual, pero este no existe, por lo que es óptimo.

No hay un algoritmo relacionado con gráficos en la serie de algoritmos codiciosos de LOCK, por lo que no haré ejercicios aquí.

Método codicioso en problemas combinatorios

Problema de mochila

Dados n artículos y una mochila con una capacidad de C, el peso del artículo i es wi, y su valor es vi. El problema de la mochila es cómo elegir los artículos que se cargarán en la mochila para que el valor total del los artículos en la mochila están maximizados?

Este problema de mochila no es un problema de mochila 0/1. Debido a que los artículos se pueden cargar parcialmente, se puede usar el método codicioso. La estrategia codiciosa es: cada vez que se selecciona el artículo con el valor de peso unitario más grande del conjunto de artículos, valor unitario = vi / wi.

  1. 1383. El valor máximo del rendimiento del equipo - códigos de dificultades Esta pregunta es No he resuelto el problema, la idea inicial de un problema. Después de leer la respuesta, lo descubrí. De hecho, es un algoritmo codicioso. Para resolver este problema, debes pensar claramente en la idea. De hecho, la idea de este problema es muy sencilla desde un punto de vista macro. Además, debes usar el montón de go de manera flexible.

Problema de programación de eventos

Hay n conjuntos de actividades E = {1,2, ……, n}, cada uno de los cuales requiere el uso del mismo recurso (como el lugar de una conferencia), y solo una actividad puede usar este recurso al mismo tiempo. Cada actividad i tiene una hora de inicio si y una hora de finalización fi que requieren el uso del recurso, y si <fi. Si se selecciona la actividad i, ocupa recursos en el intervalo de tiempo semiabierto [si, fi). Si el intervalo [si, fi) y el intervalo [sj, fj) no se cruzan, se dice que la actividad i y la actividad j son compatibles. En otras palabras, cuando si> = fj o sj> = fi, la actividad i es compatible con la actividad j. El tema de la programación de eventos requiere que se seleccione el mayor subconjunto compatible de actividades del conjunto de actividades dado.

La estrategia codiciosa razonable es: la hora de finalización más temprana, para que la siguiente actividad pueda comenzar lo antes posible.

Ordene todas las actividades según la hora de finalización más temprana y seleccione las actividades disjuntas desde el principio, que es el resultado final.

El punto problemático es cómo demostrar que la estrategia codiciosa puede calcular el resultado correcto:

  • La solución óptima general comienza con una selección codiciosa: sea E = {1,2 ……, n} un conjunto de n actividades, y las actividades en E están organizadas en un orden no decreciente del tiempo de finalización, por lo que la actividad 1 tiene la primera hora de finalización. Primero, demuestre que existe una solución óptima al problema de la programación de actividades comenzando con una elección codiciosa, es decir, la solución óptima contiene la actividad 1. Suponga que A es un subconjunto de E y una solución óptima para el problema de programación de actividades, y que las actividades en A también están organizadas en orden no decreciente del tiempo final, y la primera actividad en A es la actividad k. Si k = 1, entonces A debe seleccionar la codicia inicial óptima; si k> 1, entonces sea B = A- {k} +1, es decir, actividad 1 activa sustituida k A con la solución óptima . Dado que f1 <= fk, las actividades en B también son compatibles, y el número de actividades en B es el mismo que el número de actividades en A, por lo que B también es la solución óptima. Se puede ver que siempre hay un plan de organización de actividades óptimo que comienza con una elección codiciosa.
  • Después de hacer una elección codiciosa, el problema original se reduce a un subproblema similar en una escala más pequeña: después de seleccionar la actividad 1, el problema original se reduce a subproblemas para programar todas las actividades en E que son compatibles con la actividad 1. En otras palabras, si A es la solución óptima del problema original, entonces A 'es la solución óptima del subproblema de arreglo de actividades E' = {si> = f1, si pertenece a E}. Si no, asumiendo que B 'es la solución óptima de E', entonces B 'contiene más actividades que A', agregar la actividad 1 a B 'producirá una solución B de E, y B contiene más actividades que A, esto contradice que A es la solución óptima del problema original. Por lo tanto, el problema de caída pronunciada de elección codiciosa en cada paso se reduce a un subproblema de menor escala con la misma forma que el problema original.
  • La aplicación de la inducción matemática al número de elecciones codiciosas puede probar que el método codicioso resuelve el problema de la programación de actividades y finalmente produce la solución óptima al problema original.
  1. 1386. Disposición de los asientos del cine - Código medio

Problema de programación de varias máquinas

Hay n trabajos independientes {1,2, ……, n}, que son procesados ​​por m máquinas idénticas {M1, M2, ……, Mm}, y el tiempo de procesamiento requerido para el trabajo i bloqueo es ti (1 <= i <= n), cada trabajo se puede procesar en cualquier máquina, pero no se puede interrumpir ni dividir. El problema de programación de múltiples máquinas requiere un esquema de programación de trabajos, de modo que los n trabajos dados puedan ser procesados ​​por m máquinas en el menor tiempo posible.

El problema de la programación de varias máquinas es complicado y no existe una solución eficaz hasta el momento. Para este tipo de problema, el uso del método codicioso a veces puede obtener una mejor solución aproximada. La estrategia codiciosa del método codicioso para resolver el problema de programación de múltiples máquinas es la prioridad del trabajo de tiempo de procesamiento más largo, es decir, el trabajo con el tiempo de procesamiento más largo se asigna a la primera máquina inactiva, lo que puede garantizar que el trabajo con un tiempo de procesamiento largo El tiempo de procesamiento se procesa primero, para obtener el resultado general El tiempo de procesamiento más corto posible.

De hecho, cuando leí el capítulo del método codicioso, nunca entendí por qué el maestro usó el método codicioso para calcular los resultados correctos para muchos de los temas de este capítulo. Ahora entiendo un poco, porque la clave de este libro no es calcular el resultado correcto, sino dejarnos entender qué puede hacer el método codicioso, qué no puede hacer y hasta dónde se puede hacer. En la sociedad real, es posible que tampoco se necesite el resultado más preciso, porque algunos otros factores pueden tener un impacto mayor que si el resultado es el más exacto.

  1. 621. El programador de tareas - Código medio

para resumir

Pensé que el problema de DP era problemático, pero luego descubrí que el método codicioso era en realidad más problemático. La razón principal es que el uso del método codicioso requiere una prueba de que se puede obtener la solución óptima.

  1. Comience con una elección codiciosa
  2. Reducido a subproblemas similares en menor escala
  3. Utilice la inducción para demostrar que se puede producir la solución óptima

La prueba del método codicioso es más complicada que la de la programación dinámica, y los ejercicios de este capítulo se pueden realizar de forma más fluida sin programación dinámica. Te sugiero que practiques más el método codicioso.

Por fin

Si te gusta mi artículo, puedes seguir mi cuenta oficial (Programador Mala Tang)

Mi blog personal es: https://shidawuhen.github.io/

Revisión de artículos anteriores:

algoritmo

  1. Plan de aprendizaje de algoritmos
  2. Fuerza bruta
  3. Divide y conquistaras
  4. Método de reducción
  5. Programación dinámica
  6. Método codicioso

tecnología

  1. Marco de servicio y registro de microservicios
  2. Uso del marco de Beego
  3. Hablando de microservicios
  4. Optimización del rendimiento de TCP
  5. Realización del límite de corriente 1
  6. Redis implementa bloqueos distribuidos
  7. Seguimiento de errores del código fuente de Golang
  8. El principio de realización de la atomicidad, la coherencia y la durabilidad de las transacciones.
  9. Proceso de solicitud de CDN detallado
  10. La historia del servicio de blogs siendo aplastado
  11. Técnicas comunes de almacenamiento en caché
  12. Cómo conectarse de manera eficiente con pagos de terceros
  13. Versión concisa del marco de gin
  14. Un breve análisis de los bloqueos y transacciones de InnoDB

notas de estudio

  1. Revolución ágil
  2. Cómo ejercitar tu memoria
  3. Lógica simple después de la lectura
  4. Aire caliente después de la lectura
  5. Las Analectas-Pensamientos después de la lectura

Pensando

  1. Algunas opiniones sobre la gestión de proyectos
  2. Algunas reflexiones sobre los gerentes de producto
  3. Reflexiones sobre el desarrollo profesional de los programadores
  4. Pensando en la revisión del código
  5. Recomendación del editor de Markdown-typora

Supongo que te gusta

Origin blog.csdn.net/shida219/article/details/108969661
Recomendado
Clasificación