/// <summary> /// Executes the RAI. /// </summary> /// <param name="problem"></param> /// <param name="solver"></param> /// <param name="initial_route"></param> /// <returns></returns> private static IRoute DoSolve(RandomizedArbitraryInsertionSolver solver, IProblem problem, IRoute initial_route) { // initialize a route using best-placement. DynamicAsymmetricRoute route = null; if (initial_route == null) { OsmSharp.Math.TSP.ArbitraryInsertion.ArbitraryInsertionSolver ai_solver = new OsmSharp.Math.TSP.ArbitraryInsertion.ArbitraryInsertionSolver(); initial_route = ai_solver.Solve(problem); } // get/create the dynamic route. if (initial_route is DynamicAsymmetricRoute) { // initial route is already the correct type. route = initial_route as DynamicAsymmetricRoute; } else { // convert the initial route to a route of the correct type. route = DynamicAsymmetricRoute.CreateFrom(initial_route); } // do the Arbitrary Insertion. double weight = route.CalculateWeight(problem); int try_count = 0; while (try_count < (route.Count * route.Count)) { // keep trying for a given number of times. int factor = 2; // cut out a part. int i = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; int j = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; while (i == j) { j = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; } if (i > j) { int k = j; j = i; i = k; } // cut out the i->j part. int length = j - i; if (length > 0) { // cut and remove. DynamicAsymmetricRoute.CutResult cut_result = route.CutAndRemove( problem, weight, i, length); // calculate the weight that was removed. double new_weight = cut_result.Weight; List <int> cut_part = cut_result.CutPart; DynamicAsymmetricRoute cut_route = cut_result.Route; // use best placement to re-insert. int c = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate(cut_part.Count); while (cut_part.Count > 0) { // loop until it's empty. int customer = cut_part[c]; cut_part.RemoveAt(c); // calculate the best placement. CheapestInsertionResult result = CheapestInsertionHelper.CalculateBestPlacement( problem, cut_route, customer); //cut_route.InsertAfterAndRemove(result.CustomerBefore, result.Customer, result.CustomerAfter); cut_route.InsertAfter(result.CustomerBefore, result.Customer); new_weight = new_weight + result.Increase; // choose next random customer. c = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate(cut_part.Count); } // descide to keep new route or not. if (weight > new_weight) { route = cut_route; weight = new_weight; //if (this.CanRaiseIntermidiateResult()) //{ // this.RaiseIntermidiateResult(route.ToArray<int>(), weight); //} } } // increase the try count. try_count++; } if (solver != null && solver.CanRaiseIntermidiateResult()) { solver.RaiseIntermidiateResult(route.ToArray <int>()); } return(route); }
/// <summary> /// Executes the RAI. /// </summary> /// <param name="problem"></param> /// <param name="solver"></param> /// <param name="initial_route"></param> /// <returns></returns> private static IRoute DoSolve(RandomizedArbitraryInsertionSolver solver, IProblem problem, IRoute initial_route) { // initialize a route using best-placement. DynamicAsymmetricRoute route = null; if (initial_route == null) { OsmSharp.Math.TSP.ArbitraryInsertion.ArbitraryInsertionSolver ai_solver = new OsmSharp.Math.TSP.ArbitraryInsertion.ArbitraryInsertionSolver(); initial_route = ai_solver.Solve(problem); } // get/create the dynamic route. if (initial_route is DynamicAsymmetricRoute) { // initial route is already the correct type. route = initial_route as DynamicAsymmetricRoute; } else { // convert the initial route to a route of the correct type. route = DynamicAsymmetricRoute.CreateFrom(initial_route); } // do the Arbitrary Insertion. double weight = route.CalculateWeight(problem); int try_count = 0; while (try_count < (route.Count * route.Count)) { // keep trying for a given number of times. int factor = 2; // cut out a part. int i = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; int j = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; while (i == j) { j = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate((route.Count / factor) - 1) + 1; } if (i > j) { int k = j; j = i; i = k; } // cut out the i->j part. int length = j - i; if (length > 0) { // cut and remove. DynamicAsymmetricRoute.CutResult cut_result = route.CutAndRemove( problem, weight, i, length); // calculate the weight that was removed. double new_weight = cut_result.Weight; List<int> cut_part = cut_result.CutPart; DynamicAsymmetricRoute cut_route = cut_result.Route; // use best placement to re-insert. int c = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate(cut_part.Count); while (cut_part.Count > 0) { // loop until it's empty. int customer = cut_part[c]; cut_part.RemoveAt(c); // calculate the best placement. CheapestInsertionResult result = CheapestInsertionHelper.CalculateBestPlacement( problem, cut_route, customer); //cut_route.InsertAfterAndRemove(result.CustomerBefore, result.Customer, result.CustomerAfter); cut_route.InsertAfter(result.CustomerBefore, result.Customer); new_weight = new_weight + result.Increase; // choose next random customer. c = OsmSharp.Math.Random.StaticRandomGenerator.Get().Generate(cut_part.Count); } // descide to keep new route or not. if (weight > new_weight) { route = cut_route; weight = new_weight; //if (this.CanRaiseIntermidiateResult()) //{ // this.RaiseIntermidiateResult(route.ToArray<int>(), weight); //} } } // increase the try count. try_count++; } if (solver != null && solver.CanRaiseIntermidiateResult()) { solver.RaiseIntermidiateResult(route.ToArray<int>()); } return route; }
/// <summary> /// Executes the RAI. /// </summary> /// <param name="problem"></param> /// <param name="initial_route"></param> /// <returns></returns> public static IRoute DoSolve(IProblem problem, IRoute initial_route) { return(RandomizedArbitraryInsertionSolver.DoSolve(null, problem, initial_route)); }