Estoy implementando el algoritmo de cancelación de ciclo para encontrar una solución óptima para el problema de flujo de costo mínimo. Al encontrar y eliminar los ciclos de costos negativos en la red residual, el costo total se reduce en cada ronda. Para encontrar un ciclo negativo, estoy usando el algoritmo de Bellman-Ford.
Mi problema es: Bellman-ford solo encuentra ciclos accesibles desde la fuente, pero también necesito encontrar ciclos que no sean accesibles.
Ejemplo: en la siguiente red, ya aplicamos un flujo máximo. El borde hace muy costoso. En la red residual, tenemos un ciclo de costo negativo con capacidad . Retirarlo, nos daría una solución más barata utilizando bordes y , pero no puede llegar a ella desde la fuente .
Etiquetas: flujo / capacidad, costo
Por supuesto, podría ejecutar Bellman-Ford varias veces con cada nodo como fuente, pero eso no parece una buena solución. Estoy un poco confundido porque todos los documentos que leo parecen saltear este paso.
¿Me puede decir cómo usar bellman-ford para encontrar cada ciclo negativo (accesible o no)? Y si no es posible, ¿qué otro algoritmo propones?
fuente
Respuestas:
Para ampliar mi comentario, recuerde, este algoritmo para encontrar Flujo de Costo Mínimo se basa en el hecho de queF es máximo Al ejecutar primero Ford-Fulkerson para encontrarF y la red residual resultante solF , el costo F luego se reduce al encontrar ciclos negativos en solF . Es decir, al encontrar ciclos negativos ensolF no cambiamos la cantidad de flujo, F , pero simplemente el costo.
Ahora ejecutando Bellman-Ford det en solF podemos rastrear hacia atrás en bordes que tienen flujo no negativo (por definición de solF ) Si los ciclos son adyacentes a cualquier borde en estos caminos, entonces podemos "transferir" cierta cantidad de flujo a otros bordes en el ciclo. En otras palabras, mantenemos el flujo neto durante algún ciclo igual, pero podemos cambiar el costo.
Observe un ciclo inalcanzable desdet debe tener flujo cero. De lo contrario tendríamos una contradicción enF siendo máximo
Pido disculpas por la "ondulación manual" de esta explicación. Intentaré ser más formal cuando tenga tiempo esta noche.
fuente
Mi sugerencia: debe iniciar el algoritmo desde T para encontrar un ciclo negativo en su red residual. El resultado debe ser el mismo, pero luego puedes alcanzar el círculo
fuente
Creo que no es suficiente ejecutar Bellman-Ford desde T o S. Considere un ejemplo en el que hay una ventaja de S a T y un ciclo de costo negativo que no se puede lograr ni de S ni de T.
Una solución es agregar una S 'auxiliar y agregar una arista desde S' a cualquier otro vértice con costo 0. Luego ejecuta Bellman-Ford desde S '. De esta manera, todos los ciclos negativos son accesibles desde S '.
Además, realmente no necesita agregar ese vértice auxiliar S 'en su implementación. Simplemente inicialice d (v) = 0 para cualquier vértice v.
Vea cómo Boost Graph Library lo implementa.
fuente