Carga eficiente de autobuses

10

Esto es algo que hice para una empresa de viajes en autobús hace mucho tiempo, y nunca estuve contento con los resultados. Estaba pensando en ese viejo proyecto recientemente y pensé en revisar ese problema.

Problema:

La compañía de viajes en autobús tiene varios autobuses con diferentes capacidades de pasajeros (por ejemplo, 15 autobuses de 50 pasajeros, 25 autobuses de 30 pasajeros ... etc.). Se especializaron en ofrecer transporte a grupos muy grandes (más de 300 pasajeros por grupo). Como cada grupo necesita viajar juntos, necesitaban administrar su flota de manera eficiente para reducir el desperdicio.

Por ejemplo, 88 pasajeros están mejor atendidos por tres autobuses de 30 pasajeros (2 asientos vacíos) que por dos autobuses de 50 pasajeros (12 asientos vacíos). Otro ejemplo, 75 pasajeros estarían mejor atendidos por un autobús de 50 pasajeros y un autobús de 30 pasajeros, una combinación de tipos.

¿Qué es un buen algoritmo para hacer esto?

Se cayó el sistema
fuente
3
No para ser exigente, pero sospecho que desde el punto de vista de la compañía de autobuses, 2 autobuses de 50 pasajeros serían más eficientes ya que los costos de la gasolina solo se destinan a 2 autobuses en lugar de 3. Entonces, ¿es así como lo hizo?
Dunk
8
Esto suena como el problema de la mochila , que es NP-hard. En la práctica, su espacio de búsqueda para una ruta dada debería ser bastante pequeño.
chrisaycock
@Dunk: seré el primero en admitir que no tengo idea sobre la logística de autobuses y tours, pero ese era su requisito. Incluso tenían un consultor altamente pagado que lo hacía manualmente.
Sistema caído
Los asientos vacíos son irrelevantes, lo que cuenta son los costos operativos. Así mira la respuesta de filosodad.
Loren Pechtel
@LorenPechtel - Como dije antes, no dicto las reglas de negocio, solo las implemento.
Sistema

Respuestas:

8

Este es (más o menos) un ejemplo del problema del embalaje del contenedor, que a menudo se confunde con el problema de la mochila. En el embalaje de contenedores, tiene contenedores de cierta capacidad e intenta distribuir objetos de varios tamaños en los contenedores. La idea es utilizar el menor número posible de contenedores.

Sin embargo, no está tratando exactamente de minimizar el número de contenedores, está tratando de minimizar el número de asientos vacíos. Y es posible que esté tratando de minimizar la cantidad de asientos vacíos en la flota, es decir, que tenga cuatro grupos turísticos de varios tamaños y desee acomodarlos a todos con la menor cantidad de asientos vacíos. No puedo pensar en una instancia inmediata, pero imagino que podría ser posible construir una flota y un conjunto de grupos turísticos de tal manera que estaría mejor con una solución deficiente para algún grupo porque le permitía evitar usando una solución aún peor para algún otro grupo.

Se pone peor. ¿Qué pasa si tiene 20,30 y 50 autobuses de pasajeros? Cada uno usa diferentes cantidades de combustible, pero es más eficiente correr un 50 que correr un 20 y un 30. Pero a partir de nuestra única medida (menor número de asientos vacíos), tiene sentido correr ya sea por un 50 Tour de pasajeros.

Además, los autobuses con números extraños, como 28 o 39, sesgarían muchos de nuestros atajos.

Entonces, dependiendo de la complejidad de la situación, podría hacer una de dos cosas:

Primero, y exhaustivo árbol de búsqueda: use todas las combinaciones posibles de autobuses. Si solo tiene 3 o 4 tamaños de bus, esta es probablemente una solución razonable. De lo contrario, una disminución del ajuste óptimo produciría resultados razonables, pero no óptimos.

filosodad
fuente
No puedo imaginar por qué esta respuesta fue rechazada. Votación para compensar. Bien hecho.
David Conrad
1

Aquí hay una solución rápida y sucia en Python:

def add50(passengers, buses):
    proposed = buses + [50]
    if sum(proposed) < passengers:
        return add50(passengers, proposed)
    return proposed

def add30(passengers, buses):
    proposed = buses + [30]
    if sum(proposed) < passengers:
        proposed30 = add30(passengers, proposed)
        proposed50 = add50(passengers, proposed)
        return proposed30 if sum(proposed30) < sum(proposed50) else proposed50
    return proposed

print add30(88, [])
print add30(75, [])
print add30(105, [])

Cuando lo ejecuto, obtengo:

[30, 30, 30]
[30, 50]
[30, 30, 50]

El código está haciendo una búsqueda profunda a través de los posibles escenarios. Dado que el orden no importa ( [30, 50]es lo mismo que [50, 30]), podemos hacer que el espacio de búsqueda sea mucho más pequeño solo agregando buses del mismo tamaño o más grandes. Es por eso que add30()puede llamar add50(), pero no al revés.

chrisaycock
fuente
0

Voy a responder esto desde la perspectiva del cliente. No quisiera un algoritmo codificado para esta aplicación. Hay demasiadas variables que pueden cambiar con el tiempo. Aunque nada sobre sus autobuses puede cambiar el peso de los factores podría cambiar o podrían descubrirse nuevos factores en los que nunca pensé (por ejemplo, tiempo extra, leyes y otros costos del conductor).

Debido a esto, me gustaría poder crear mi propia tabla de búsqueda basada en un rango del número de pasajeros solicitados y crearía mi propia configuración para las mejores combinaciones de autobús. Ejemplo: 31-50 = 1 X 50, 51-60 = 2 X 30. ¿Esto realmente necesita ser calculado? Es más fácil cambiar la configuración que un montón de fórmulas que factorizan asientos, gasolina y conductores. Encuentre la mejor combinación y termine con ella y tenga mucho espacio para que el usuario cambie esta configuración como mejor le parezca.

Se pueden descubrir nuevos factores. ¿Los autobuses más grandes pagan una tasa exponencialmente más alta en los peajes? ¿Puedo obtener conductores menos costosos para autobuses pequeños cuando se aplica una nueva ley para la certificación y licencia adicional para los conductores de autobuses de más de 30 pasajeros?

Contratan a un nuevo consultor con una lógica diferente a su fórmula y es posible que sea necesario reescribir su aplicación. ¿Quiere decir que tiene que factorizar el costo del estacionamiento?

JeffO
fuente
Esto no funciona: 31-50 = autobús de 50 asientos, a menos que ya se usen para otros grupos, o estén fuera de servicio o no estén disponibles por otros motivos. La compañía de autobuses de la pregunta, con 15 autobuses de 50 pasajeros es muy probable que tenga varios clientes a la vez.
MSalters