首页 > 解决方案 > 将 Python OR Tools 路由解决方案保存到列表中

问题描述

我刚刚开始使用 OR Tools 进行路线优化,基于此文档:

或工具旅行销售问题

我非常兴奋能够让它工作并返回看似最佳的结果,但现在我遇到了一个意想不到的问题。我需要将结果转换为有意义的字符串或列表或字典,但它不会让我做任何事情,除了它应该运行的序列,但它不会让我将它保存在我的代码中原因。

如果我这样做:

if solution:
     print_solution(manager, routing, solution)

我明白了:

Objective: 115 miles
Route for vehicle 0:
 0 -> 34 -> 27 -> 13 -> 8 -> 37 -> 36 -> 4 -> 30 -> 19 -> 18 -> 7 -> 9 -> 31 -> 35 -> 28 -> 38 -> 23 -> 25 -> 24 -> 16 -> 3 -> 21 -> 2 -> 32 -> 29 -> 17 -> 14 -> 11 -> 12 -> 6 -> 15 -> 5 -> 10 -> 26 -> 33 -> 1 -> 22 -> 20 -> 0

我什至无法将该解决方案保存为文本。试

solution = print_solution(manager, routing, solution)

不起作用。解决方案变量下不会保存任何内容。

我想通了:

str(solution) 

产生一个这样的字符串,但它甚至不符合上面的序列或没有任何意义:

Assignment(Nexts0 (34) | Nexts1 (22) | Nexts2 (32) | Nexts3 (21) | Nexts4 (30) | Nexts5 (10) | Nexts6 (15) | Nexts7 (9) | Nexts8 (37) | Nexts9 (31) | Nexts10 (26) | Nexts11 (12) | Nexts12 (6) | Nexts13 (8) | Nexts14 (11) | Nexts15 (5) | Nexts16 (3) | Nexts17 (14) | Nexts18 (7) | Nexts19 (18) | Nexts20 (39) | Nexts21 (2) | Nexts22 (20) | Nexts23 (25) | Nexts24 (16) | Nexts25 (24) | Nexts26 (33) | Nexts27 (13) | Nexts28 (38) | Nexts29 (17) | Nexts30 (19) | Nexts31 (35) | Nexts32 (29) | Nexts33 (1) | Nexts34 (27) | Nexts35 (28) | Nexts36 (4) | Nexts37 (36) | Nexts38 (23) | Active0 (1) | Active1 (1) | Active2 (1) | Active3 (1) | Active4 (1) | Active5 (1) | Active6 (1) | Active7 (1) | Active8 (1) | Active9 (1) | Active10 (1) | Active11 (1) | Active12 (1) | Active13 (1) | Active14 (1) | Active15 (1) | Active16 (1) | Active17 (1) | Active18 (1) | Active19 (1) | Active20 (1) | Active21 (1) | Active22 (1) | Active23 (1) | Active24 (1) | Active25 (1) | Active26 (1) | Active27 (1) | Active28 (1) | Active29 (1) | Active30 (1) | Active31 (1) | Active32 (1) | Active33 (1) | Active34 (1) | Active35 (1) | Active36 (1) | Active37 (1) | Active38 (1) | Vehicles0 (0) | Vehicles1 (0) | Vehicles2 (0) | Vehicles3 (0) | Vehicles4 (0) | Vehicles5 (0) | Vehicles6 (0) | Vehicles7 (0) | Vehicles8 (0) | Vehicles9 (0) | Vehicles10 (0) | Vehicles11 (0) | Vehicles12 (0) | Vehicles13 (0) | Vehicles14 (0) | Vehicles15 (0) | Vehicles16 (0) | Vehicles17 (0) | Vehicles18 (0) | Vehicles19 (0) | Vehicles20 (0) | Vehicles21 (0) | Vehicles22 (0) | Vehicles23 (0) | Vehicles24 (0) | Vehicles25 (0) | Vehicles26 (0) | Vehicles27 (0) | Vehicles28 (0) | Vehicles29 (0) | Vehicles30 (0) | Vehicles31 (0) | Vehicles32 (0) | Vehicles33 (0) | Vehicles34 (0) | Vehicles35 (0) | Vehicles36 (0) | Vehicles37 (0) | Vehicles38 (0) | Vehicles39 (0) | (115))

我经历了一个大过程,将该字符串转换为车辆应该访问的序列列表,但后来我意识到它与上面的解决方案不对应。34是第一站,然后是27,这个显示22。

如何将 OR 工具结果转换为有用的实际字典或列表?我需要把它变成我们可以在更大范围内使用的东西。

标签: pythontraveling-salesmanor-tools

解决方案


您只需要解析打印路线的代码:

def print_solution(manager, routing, solution):
    """Prints solution on console."""
    print('Objective: {} miles'.format(solution.ObjectiveValue()))
    index = routing.Start(0)
    plan_output = 'Route for vehicle 0:\n'
    route_distance = 0
    while not routing.IsEnd(index):
        plan_output += ' {} ->'.format(manager.IndexToNode(index))
        previous_index = index
        index = solution.Value(routing.NextVar(index))
        route_distance += routing.GetArcCostForVehicle(previous_index, index, 0)
    plan_output += ' {}\n'.format(manager.IndexToNode(index))
    print(plan_output)
    plan_output += 'Route distance: {}miles\n'.format(route_distance)

并用一些将路线存储到列表中的代码替换打印部分。


推荐阅读