如何解决或工具-VRP-处理找不到最佳解决方案的情况
我正在基于Google的ORTools为车辆路径问题构建求解器。
对于简单的问题或大容量的问题,它可以很好地工作,但是对于大多数“真实”数据集,我最终都会获得无限期运行或超时的解决方案。
经过一些思考,我意识到并不是所有现实世界的问题都可以解决或达到最佳。例如。我可能希望大多数车辆每天行驶不超过500公里。但是,如果我必须将货物运送给600公里以外的人,则整个解决方案将失败。
如何处理这些情况?现在看来,这是二进制的通过或失败。对于某些情况被忽略或返回次优解决方案,我感到非常高兴。
public List<OptimisedVehicleRoute> Start(Location depot,List<Location> locations,int numVehicles = 1,float maxdistanceKmPerVehicle = 1000f,float maxdistanceKmSlack = 5f)
{
// Create Routing Index Manager
var depotIndex = locations.IndexOf(depot);
var manager = new RoutingIndexManager(locations.Count,numVehicles,depotIndex);
Console.WriteLine($"Depot at {depot.Postcode}");
var routing = new RoutingModel(manager);
var numCalls = 0l;
int transitCallbackIndex = routing.RegisterTransitCallback((long fromIndex,long toIndex) =>
{
numCalls++;
// Convert from routing variable Index to distance matrix NodeIndex.
var fromNode = manager.IndexToNode(fromIndex);
var toNode = manager.IndexToNode(toIndex);
var fromLocation = locations[fromNode];
var toLocation = locations[toNode];
var mdistance = fromLocation.distanceto(toLocation);
return mdistance;
});
// The arc cost evaluator tells the solver how to calculate the cost of travel between any two locations
routing.SetArcCostEvaluatorOfAllVehicles(transitCallbackIndex);
long maxVehicledistanceSlack = (long)Math.Round(maxdistanceKmSlack * 1000); // slack per day
long maxVehicledistance = (long)Math.Round(maxdistanceKmPerVehicle * 1000); // 1000km max distance per day
routing.AddDimension(transitCallbackIndex,maxVehicledistanceSlack,maxVehicledistance,true,"distance");
RoutingDimension distanceDimension = routing.GetMutableDimension("distance");
distanceDimension.SetGlobalSpanCostCoefficient(100);
var searchParameters = operations_research_constraint_solver.DefaultRoutingSearchParameters();
searchParameters.FirstSolutionStrategy = FirstSolutionStrategy.Types.Value.PathCheapestArc;
var timer = new Stopwatch();
timer.Start();
searchParameters.LogSearch = true;
var solution = routing.solveWithParameters(searchParameters);
timer.Stop();
Console.WriteLine(timer.Elapsed.TotalSeconds);
var optimisedVehicleRoutes = this.CreateOptimisedVehicleLocations(locations,routing,manager,solution);
this.OptimiseddistanceKm = optimisedVehicleRoutes.Sum(r => r.TotaldistanceKm);
routing.dispose();
return optimisedVehicleRoutes;
}
P.s。如果有人可以帮助我了解“ Slack”实际上是用于什么的,我将不胜感激。我最初假设这是每辆车的公差(即10 km的松弛度可使该车辆在其最大路线距离上行驶10 km)。但是现在我不确定
解决方法
如果您的位置在600公里,最大允许距离为500公里,那么您的问题基本上是不可行的...
但是您可以使用AddDisjunction()
允许求解器放置该位置,从而使问题变得可行...
请在文档站点上查看我们的示例:https://developers.google.com/optimization/routing/penalties
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。