|
11 | 11 | // See the License for the specific language governing permissions and |
12 | 12 | // limitations under the License. |
13 | 13 |
|
14 | | -/// The vehicle routing library lets one model and solve generic vehicle routing |
15 | | -/// problems ranging from the Traveling Salesman Problem to more complex |
16 | | -/// problems such as the Capacitated Vehicle Routing Problem with Time Windows. |
17 | | -/// |
18 | | -/// The objective of a vehicle routing problem is to build routes covering a set |
19 | | -/// of nodes minimizing the overall cost of the routes (usually proportional to |
20 | | -/// the sum of the lengths of each segment of the routes) while respecting some |
21 | | -/// problem-specific constraints (such as the length of a route). A route is |
22 | | -/// equivalent to a path connecting nodes, starting/ending at specific |
23 | | -/// starting/ending nodes. |
24 | | -/// |
25 | | -/// The term "vehicle routing" is historical and the category of problems solved |
26 | | -/// is not limited to the routing of vehicles: any problem involving finding |
27 | | -/// routes visiting a given number of nodes optimally falls under this category |
28 | | -/// of problems, such as finding the optimal sequence in a playlist. |
29 | | -/// The literature around vehicle routing problems is extremely dense but one |
30 | | -/// can find some basic introductions in the following links: |
31 | | -/// - http://en.wikipedia.org/wiki/Travelling_salesman_problem |
32 | | -/// - http://en.wikipedia.org/wiki/Vehicle_routing_problem |
33 | | -/// |
34 | | -/// The vehicle routing library is a vertical layer above the constraint |
35 | | -/// programming library (ortools/constraint_programming:cp). |
36 | | -/// One has access to all underlying constrained variables of the vehicle |
37 | | -/// routing model which can therefore be enriched by adding any constraint |
38 | | -/// available in the constraint programming library. |
39 | | -/// |
40 | | -/// There are two sets of variables available: |
41 | | -/// - path variables: |
42 | | -/// * "next(i)" variables representing the immediate successor of the node |
43 | | -/// corresponding to i; use IndexToNode() to get the node corresponding to |
44 | | -/// a "next" variable value; note that node indices are strongly typed |
45 | | -/// integers (cf. ortools/base/int_type.h); |
46 | | -/// * "vehicle(i)" variables representing the vehicle route to which the |
47 | | -/// node corresponding to i belongs; |
48 | | -/// * "active(i)" boolean variables, true if the node corresponding to i is |
49 | | -/// visited and false if not; this can be false when nodes are either |
50 | | -/// optional or part of a disjunction; |
51 | | -/// * The following relationships hold for all i: |
52 | | -/// active(i) == 0 <=> next(i) == i <=> vehicle(i) == -1, |
53 | | -/// next(i) == j => vehicle(j) == vehicle(i). |
54 | | -/// - dimension variables, used when one is accumulating quantities along |
55 | | -/// routes, such as weight or volume carried, distance or time: |
56 | | -/// * "cumul(i,d)" variables representing the quantity of dimension d when |
57 | | -/// arriving at the node corresponding to i; |
58 | | -/// * "transit(i,d)" variables representing the quantity of dimension d added |
59 | | -/// after visiting the node corresponding to i. |
60 | | -/// * The following relationship holds for all (i,d): |
61 | | -/// next(i) == j => cumul(j,d) == cumul(i,d) + transit(i,d). |
62 | | -/// Solving the vehicle routing problems is mainly done using approximate |
63 | | -/// methods (namely local search, |
64 | | -/// cf. http://en.wikipedia.org/wiki/Local_search_(optimization) ), potentially |
65 | | -/// combined with exact techniques based on dynamic programming and exhaustive |
66 | | -/// tree search. |
67 | | -// TODO(user): Add a section on costs (vehicle arc costs, span costs, |
68 | | -// disjunctions costs). |
69 | | -// |
70 | | -/// Advanced tips: Flags are available to tune the search used to solve routing |
71 | | -/// problems. Here is a quick overview of the ones one might want to modify: |
72 | | -/// - Limiting the search for solutions: |
73 | | -/// * routing_solution_limit (default: kint64max): stop the search after |
74 | | -/// finding 'routing_solution_limit' improving solutions; |
75 | | -/// * routing_time_limit (default: kint64max): stop the search after |
76 | | -/// 'routing_time_limit' milliseconds; |
77 | | -/// - Customizing search: |
78 | | -/// * routing_first_solution (default: select the first node with an unbound |
79 | | -/// successor and connect it to the first available node): selects the |
80 | | -/// heuristic to build a first solution which will then be improved by local |
81 | | -/// search; possible values are GlobalCheapestArc (iteratively connect two |
82 | | -/// nodes which produce the cheapest route segment), LocalCheapestArc |
83 | | -/// (select the first node with an unbound successor and connect it to the |
84 | | -/// node which produces the cheapest route segment), PathCheapestArc |
85 | | -/// (starting from a route "start" node, connect it to the node which |
86 | | -/// produces the cheapest route segment, then extend the route by iterating |
87 | | -/// on the last node added to the route). |
88 | | -/// * Local search neighborhoods: |
89 | | -/// - routing_no_lns (default: false): forbids the use of Large Neighborhood |
90 | | -/// Search (LNS); LNS can find good solutions but is usually very slow. |
91 | | -/// Refer to the description of PATHLNS in the LocalSearchOperators enum |
92 | | -/// in constraint_solver.h for more information. |
93 | | -/// - routing_no_tsp (default: true): forbids the use of exact methods to |
94 | | -/// solve "sub"-traveling salesman problems (TSPs) of the current model |
95 | | -/// (such as sub-parts of a route, or one route in a multiple route |
96 | | -/// problem). Uses dynamic programming to solve such TSPs with a maximum |
97 | | -/// size (in number of nodes) up to cp_local_search_tsp_opt_size (flag |
98 | | -/// with a default value of 13 nodes). It is not activated by default |
99 | | -/// because it can slow down the search. |
100 | | -/// * Meta-heuristics: used to guide the search out of local minima found by |
101 | | -/// local search. Note that, in general, a search with metaheuristics |
102 | | -/// activated never stops, therefore one must specify a search limit. |
103 | | -/// Several types of metaheuristics are provided: |
104 | | -/// - routing_guided_local_search (default: false): activates guided local |
105 | | -/// search (cf. http://en.wikipedia.org/wiki/Guided_Local_Search); |
106 | | -/// this is generally the most efficient metaheuristic for vehicle |
107 | | -/// routing; |
108 | | -/// - routing_simulated_annealing (default: false): activates simulated |
109 | | -/// annealing (cf. http://en.wikipedia.org/wiki/Simulated_annealing); |
110 | | -/// - routing_tabu_search (default: false): activates tabu search (cf. |
111 | | -/// http://en.wikipedia.org/wiki/Tabu_search). |
112 | | -/// |
113 | | -/// Code sample: |
114 | | -/// Here is a simple example solving a traveling salesman problem given a cost |
115 | | -/// function callback (returns the cost of a route segment): |
116 | | -/// |
117 | | -/// - Define a custom distance/cost function from an index to another; in this |
118 | | -/// example just returns the sum of the indices: |
119 | | -/// |
120 | | -/// int64_t MyDistance(int64_t from, int64_t to) { |
121 | | -/// return from + to; |
122 | | -/// } |
123 | | -/// |
124 | | -/// - Create a routing model for a given problem size (int number of nodes) and |
125 | | -/// number of routes (here, 1): |
126 | | -/// |
127 | | -/// RoutingIndexManager manager(...number of nodes..., 1); |
128 | | -/// RoutingModel routing(manager); |
129 | | -/// |
130 | | -/// - Set the cost function by registering an std::function<int64_t(int64_t, |
131 | | -/// int64_t)> in the model and passing its index as the vehicle cost. |
132 | | -/// |
133 | | -/// const int cost = routing.RegisterTransitCallback(MyDistance); |
134 | | -/// routing.SetArcCostEvaluatorOfAllVehicles(cost); |
135 | | -/// |
136 | | -/// - Find a solution using Solve(), returns a solution if any (owned by |
137 | | -/// routing): |
138 | | -/// |
139 | | -/// const Assignment* solution = routing.Solve(); |
140 | | -/// CHECK(solution != nullptr); |
141 | | -/// |
142 | | -/// - Inspect the solution cost and route (only one route here): |
143 | | -/// |
144 | | -/// LOG(INFO) << "Cost " << solution->ObjectiveValue(); |
145 | | -/// const int route_number = 0; |
146 | | -/// for (int64_t node = routing.Start(route_number); |
147 | | -/// !routing.IsEnd(node); |
148 | | -/// node = solution->Value(routing.NextVar(node))) { |
149 | | -/// LOG(INFO) << manager.IndexToNode(node); |
150 | | -/// } |
151 | | -/// |
152 | | -/// |
153 | | -/// Keywords: Vehicle Routing, Traveling Salesman Problem, TSP, VRP, CVRPTW, |
154 | | -/// PDP. |
| 14 | +/** @file routing.h |
| 15 | +@brief The vehicle routing library lets one model and solve generic vehicle |
| 16 | +routing problems ranging from the Traveling Salesman Problem to more complex |
| 17 | +problems such as the Capacitated Vehicle Routing Problem with Time Windows. |
| 18 | +@details The objective of a vehicle routing problem is to build routes covering |
| 19 | +a set of nodes minimizing the overall cost of the routes (usually proportional |
| 20 | +to the sum of the lengths of each segment of the routes) while respecting some |
| 21 | +problem-specific constraints (such as the length of a route). A route is |
| 22 | +equivalent to a path connecting nodes, starting/ending at specific |
| 23 | +starting/ending nodes.\n |
| 24 | +The term "vehicle routing" is historical and the category of problems solved |
| 25 | +is not limited to the routing of vehicles: any problem involving finding |
| 26 | +routes visiting a given number of nodes optimally falls under this category |
| 27 | +of problems, such as finding the optimal sequence in a playlist.\n |
| 28 | +The literature around vehicle routing problems is extremely dense but one |
| 29 | +can find some basic introductions in the following links: |
| 30 | +- http://en.wikipedia.org/wiki/Travelling_salesman_problem |
| 31 | +- http://en.wikipedia.org/wiki/Vehicle_routing_problem |
| 32 | +
|
| 33 | +The vehicle routing library is a vertical layer above the constraint |
| 34 | +programming library (ortools/constraint_programming:cp).\n |
| 35 | +One has access to all underlying constrained variables of the vehicle |
| 36 | +routing model which can therefore be enriched by adding any constraint |
| 37 | +available in the constraint programming library.\n |
| 38 | +There are two sets of variables available: |
| 39 | +- path variables: |
| 40 | + - "next(i)" variables representing the immediate successor of the node |
| 41 | + corresponding to i; use IndexToNode() to get the node corresponding to |
| 42 | + a "next" variable value; note that node indices are strongly typed |
| 43 | + integers (cf. ortools/base/int_type.h); |
| 44 | + - "vehicle(i)" variables representing the vehicle route to which the |
| 45 | + node corresponding to i belongs; |
| 46 | + - "active(i)" boolean variables, true if the node corresponding to i is |
| 47 | + visited and false if not; this can be false when nodes are either |
| 48 | + optional or part of a disjunction; |
| 49 | + - The following relationships hold for all i: |
| 50 | + active(i) == 0 <=> next(i) == i <=> vehicle(i) == -1, |
| 51 | + next(i) == j => vehicle(j) == vehicle(i). |
| 52 | +- dimension variables, used when one is accumulating quantities along |
| 53 | + routes, such as weight or volume carried, distance or time: |
| 54 | + - "cumul(i,d)" variables representing the quantity of dimension d when |
| 55 | + arriving at the node corresponding to i; |
| 56 | + - "transit(i,d)" variables representing the quantity of dimension d added |
| 57 | + after visiting the node corresponding to i. |
| 58 | + - The following relationship holds for all (i,d): |
| 59 | + next(i) == j => cumul(j,d) == cumul(i,d) + transit(i,d). |
| 60 | +
|
| 61 | +Solving the vehicle routing problems is mainly done using approximate |
| 62 | +methods (namely local search, |
| 63 | +cf. http://en.wikipedia.org/wiki/Local_search_(optimization) ), potentially |
| 64 | +combined with exact techniques based on dynamic programming and exhaustive |
| 65 | +tree search. |
| 66 | +TODO(user): Add a section on costs (vehicle arc costs, span costs, |
| 67 | + disjunctions costs). |
| 68 | +Advanced tips: Flags are available to tune the search used to solve routing |
| 69 | +problems. Here is a quick overview of the ones one might want to modify: |
| 70 | +- Limiting the search for solutions: |
| 71 | + - routing_solution_limit (default: kint64max): stop the search after |
| 72 | + finding 'routing_solution_limit' improving solutions; |
| 73 | + - routing_time_limit (default: kint64max): stop the search after |
| 74 | + 'routing_time_limit' milliseconds; |
| 75 | +- Customizing search: |
| 76 | + - routing_first_solution (default: select the first node with an unbound |
| 77 | + successor and connect it to the first available node): selects the |
| 78 | + heuristic to build a first solution which will then be improved by local |
| 79 | + search; possible values are GlobalCheapestArc (iteratively connect two |
| 80 | + nodes which produce the cheapest route segment), LocalCheapestArc |
| 81 | + (select the first node with an unbound successor and connect it to the |
| 82 | + node which produces the cheapest route segment), PathCheapestArc |
| 83 | + (starting from a route "start" node, connect it to the node which |
| 84 | + produces the cheapest route segment, then extend the route by iterating |
| 85 | + on the last node added to the route). |
| 86 | + - Local search neighborhoods: |
| 87 | + - routing_no_lns (default: false): forbids the use of Large Neighborhood |
| 88 | + Search (LNS); LNS can find good solutions but is usually very slow. |
| 89 | + Refer to the description of PATHLNS in the LocalSearchOperators enum |
| 90 | + in constraint_solver.h for more information. |
| 91 | + - routing_no_tsp (default: true): forbids the use of exact methods to |
| 92 | + solve "sub"-traveling salesman problems (TSPs) of the current model |
| 93 | + (such as sub-parts of a route, or one route in a multiple route |
| 94 | + problem). Uses dynamic programming to solve such TSPs with a maximum |
| 95 | + size (in number of nodes) up to cp_local_search_tsp_opt_size (flag |
| 96 | + with a default value of 13 nodes). It is not activated by default |
| 97 | + because it can slow down the search. |
| 98 | + - Meta-heuristics: used to guide the search out of local minima found by |
| 99 | + local search. Note that, in general, a search with metaheuristics |
| 100 | + activated never stops, therefore one must specify a search limit. |
| 101 | + Several types of metaheuristics are provided: |
| 102 | + - routing_guided_local_search (default: false): activates guided local |
| 103 | + search (cf. http://en.wikipedia.org/wiki/Guided_Local_Search); |
| 104 | + this is generally the most efficient metaheuristic for vehicle |
| 105 | + routing; |
| 106 | + - routing_simulated_annealing (default: false): activates simulated |
| 107 | + annealing (cf. http://en.wikipedia.org/wiki/Simulated_annealing); |
| 108 | + - routing_tabu_search (default: false): activates tabu search (cf. |
| 109 | + http://en.wikipedia.org/wiki/Tabu_search). |
| 110 | +
|
| 111 | +Code sample:\n |
| 112 | +Here is a simple example solving a traveling salesman problem given a cost |
| 113 | +function callback (returns the cost of a route segment): |
| 114 | +- Define a custom distance/cost function from an index to another; in this |
| 115 | + example just returns the sum of the indices: |
| 116 | + @code{.cpp} |
| 117 | + int64_t MyDistance(int64_t from, int64_t to) { |
| 118 | + return from + to; |
| 119 | + } |
| 120 | + @endcode |
| 121 | +- Create a routing model for a given problem size (int number of nodes) and |
| 122 | + number of routes (here, 1): |
| 123 | + @code{.cpp} |
| 124 | + RoutingIndexManager manager(...number of nodes..., 1); |
| 125 | + RoutingModel routing(manager); |
| 126 | + @endcode |
| 127 | +- Set the cost function by registering an std::function<int64_t(int64_t, |
| 128 | +int64_t)> in the model and passing its index as the vehicle cost. |
| 129 | + @code{.cpp} |
| 130 | + const int cost = routing.RegisterTransitCallback(MyDistance); |
| 131 | + routing.SetArcCostEvaluatorOfAllVehicles(cost); |
| 132 | + @endcode |
| 133 | +- Find a solution using Solve(), returns a solution if any (owned by |
| 134 | + routing): |
| 135 | + @code{.cpp} |
| 136 | + const Assignment* solution = routing.Solve(); |
| 137 | + CHECK(solution != nullptr); |
| 138 | + @endcode |
| 139 | +- Inspect the solution cost and route (only one route here): |
| 140 | + @code{.cpp} |
| 141 | + LOG(INFO) << "Cost " << solution->ObjectiveValue(); |
| 142 | + const int route_number = 0; |
| 143 | + for (int64_t node = routing.Start(route_number); |
| 144 | + !routing.IsEnd(node); |
| 145 | + node = solution->Value(routing.NextVar(node))) { |
| 146 | + LOG(INFO) << manager.IndexToNode(node); |
| 147 | + } |
| 148 | + @endcode |
| 149 | +Keywords: Vehicle Routing, Traveling Salesman Problem, TSP, VRP, CVRPTW, PDP. |
| 150 | +*/ |
155 | 151 |
|
156 | 152 | #ifndef ORTOOLS_CONSTRAINT_SOLVER_ROUTING_H_ |
157 | 153 | #define ORTOOLS_CONSTRAINT_SOLVER_ROUTING_H_ |
@@ -887,7 +883,7 @@ class OR_DLL RoutingModel { |
887 | 883 | enum PenaltyCostBehavior { PENALIZE_ONCE, PENALIZE_PER_INACTIVE }; |
888 | 884 |
|
889 | 885 | /// @brief Adds a disjunction constraint on the indices. |
890 | | - /// @details exactly 'max_cardinality' of the indices are active. |
| 886 | + /// @details Exactly 'max_cardinality' of the indices are active. |
891 | 887 | /// |
892 | 888 | /// If a penalty is given, at most 'max_cardinality' of the indices can be |
893 | 889 | /// active, and if less are active, 'penalty' is payed per inactive index if |
@@ -1093,10 +1089,8 @@ class OR_DLL RoutingModel { |
1093 | 1089 | /// Set the node visit types and incompatibilities/requirements between the |
1094 | 1090 | /// types (see below). |
1095 | 1091 | /// |
1096 | | - /// NOTE: Before adding any incompatibilities and/or requirements on types: |
1097 | | - /// 1) All corresponding node types must have been set. |
1098 | | - /// 2) CloseVisitTypes() must be called so all containers are resized |
1099 | | - /// accordingly. |
| 1092 | + /// NOTE: Before adding any incompatibilities and/or requirements on types, |
| 1093 | + /// all corresponding node types must have been set. |
1100 | 1094 | /// |
1101 | 1095 | /// The following enum is used to describe how a node with a given type 'T' |
1102 | 1096 | /// impacts the number of types 'T' on the route when visited, and thus |
|
0 commit comments