具有距离和时间限制的车辆路径问题Ortools

时间:2020-05-29 01:01:35

标签: python or-tools vehicle-routing

我想制作一个简单的VRP,同时将距离最小化,同时跟踪每个节点的时间限制。问题是我随时间流逝做了VRP教程中所说的内容,但是那是行不通的。输出给我:

Day: 0, ((0, 7)) Item: 3
Day: 1, ((0, 4)) Item: 3
Day: 2, ((0, 7)) Item: 0
Day: 3, ((0, 1)) Item: 2
Day: 4, ((0, 7)) Item: 2
Day: 5, ((0, 7)) Item: 0
Day: 6, ((0, 3)) Item: 1

(((x,y))值是节点的时间范围值(可以正确读取),但使用不正确,例如,节点2在第3天,即使其限制在0到1之间。

from __future__ import print_function
from ortools.constraint_solver import routing_enums_pb2
from ortools.constraint_solver import pywrapcp

def create_data_model():
    """Stores the data for the problem."""
    data = {}
    data['distance_matrix'] = [
        [0, 0, 0, 0, 0, 0, 0, 0], 
        [0, 0, 0, 0, 0, 0, 0, 0], 
        [0, 0, 0, 1, 1, 1, 1, 1], 
        [0, 0, 0, 0, 20, 20, 30, 30],
        [0, 0, 0, 10, 0, 0, 30, 30],
        [0, 0, 0, 10, 0, 0, 30, 30],
        [0, 0, 0, 10, 20, 20, 0, 0],
        [0, 0, 0, 10, 20, 20, 0, 0],
    ]
    data['deadlines'] = [
        (0, 7), # 0 - 1
        (0, 7), # 0 - 2
        (0, 3), # 1 - 3
        (0, 7), # 2 - 4
        (0, 1), # 2 - 5
        (0, 4), # 3 - 6
        (0, 7), # 3 - 7
    ]
    data['num_items'] = 5
    data['num_days'] = 7
    data['types'] = [0,0,1,2,2,3,3]
    data['num_vehicles'] = 1
    data['depot'] = 0
    data['storage_cost'] = 10
    return data


def print_solution(data, manager, routing, solution):
    """Prints solution on console."""
    time_dimension = routing.GetDimensionOrDie('Time')
    print(routing.status())
    max_route_distance = 0
    for vehicle_id in range(data['num_vehicles']):
        index = routing.Start(vehicle_id)
        plan_output = 'Schedule: \n'
        route_distance = 0
        previous_index = index
        index = solution.Value(routing.NextVar(index))
        day = 0
        while not routing.IsEnd(index):
            time_var = time_dimension.CumulVar(index)
            print(time_var)
            plan_output += 'Day: {0}, ({1}) Item: {2} \n'.format(day, data['deadlines'][index-1], data['types'][manager.IndexToNode(index)-1])
            previous_index = index
            index = solution.Value(routing.NextVar(index))
            print(index)
            route_distance += routing.GetArcCostForVehicle(previous_index, index, vehicle_id)
            day += 1
        plan_output += 'Cost : {}\n'.format(route_distance)
        print(plan_output)
        max_route_distance = max(route_distance, max_route_distance)
        #total_time += solution.Min(time_var)
    #print('Total time of all routes: {} days'.format(total_time))
    print('Minimum cost: {}'.format(max_route_distance))




def main():
    """Solve the CVRP problem."""
    # Instantiate the data problem.
    data = create_data_model()

    # Create the routing index manager.
    manager = pywrapcp.RoutingIndexManager(data['num_days']+1,
                                           data['num_vehicles'], data['depot'])

    # Create Routing Model.
    routing = pywrapcp.RoutingModel(manager)

    # --- DISTANCE ---
    # Create and register a transit callback.
    def distance_callback(from_index, to_index):
        """Returns the distance between the two nodes."""
        from_node = manager.IndexToNode(from_index)
        to_node = manager.IndexToNode(to_index)
       # storage = (7 - day)*data['storage_cost']
        return data['distance_matrix'][from_node][to_node]

    transit_callback_index = routing.RegisterTransitCallback(distance_callback)
    routing.SetArcCostEvaluatorOfAllVehicles(transit_callback_index)


    # --- TIME ---
    #Add Time Windows constraint.
     def time_callback(index):
         return 1
     transit_callback_index = routing.RegisterPositiveUnaryTransitCallback(time_callback)
     time = 'Time'
     routing.AddDimension(
         transit_callback_index,
         0,  # allow waiting time
         data['num_days'],  # maximum time per vehicle
         True,
         time)
    time_dimension = routing.GetDimensionOrDie(time)
    # Add time window constraints for each location except depot.
    for location_idx, time_window in enumerate(data['deadlines']):
        index = manager.NodeToIndex(location_idx)
        time_dimension.CumulVar(index).SetRange(time_window[0], time_window[1])
    # Add time window constraints for each vehicle start node.
    time_dimension.CumulVar(routing.Start(0)).SetRange(data['deadlines'][0][0], data['deadlines'][0][1])


    # Instantiate route start and end times to produce feasible times.
    #routing.AddVariableMinimizedByFinalizer(time_dimension.CumulVar(routing.Start(0)))
    #routing.AddVariableMinimizedByFinalizer(time_dimension.CumulVar(routing.End(0)))



    # Setting first solution heuristic.
    search_parameters = pywrapcp.DefaultRoutingSearchParameters()
    search_parameters.first_solution_strategy = (
        routing_enums_pb2.FirstSolutionStrategy.PATH_CHEAPEST_ARC)

    # Solve the problem.
    solution = routing.SolveWithParameters(search_parameters)

    # Print solution on console.
    if solution:
        print_solution(data, manager, routing, solution)
    else:
        print('No solution')


if __name__ == '__main__':
    main()

0 个答案:

没有答案