public static DVRP Parse(string input) { if (String.IsNullOrWhiteSpace(input)) { throw new ArgumentException(input); } var instance = new DVRP(); var lines = input.Split(new[] { '\n' }); for (int i = 0; i < lines.Length; i++) { string[] split = DVRPHelper.SplitText(lines[i]); switch (split[0]) { case "VRPTEST": instance.FormatVersionNumber = split[1]; break; case "COMMENT": instance.Comment += lines[i].Substring(9, lines[i].Length - 9).Trim(new Char[] { ' ', '\r' }); // split[j] + " "; break; case "NAME": instance.Name = split[1]; break; case "NUM_DEPOTS": instance.NumDepots = int.Parse(split[1]); instance.Depots = new Depot[instance.NumDepots]; break; case "NUM_CAPACITIES": instance.NumCapacities = int.Parse(split[1]); break; case "NUM_VISITS": instance.NumVistis = int.Parse(split[1]); instance.Clients = new Client[instance.NumVistis]; instance.ClientID = new int[instance.NumVistis]; break; case "NUM_LOCATIONS": instance.NumLocations = int.Parse(split[1]); instance.Locations = new Location[instance.NumLocations]; break; case "NUM_VEHICLES": instance.NumVehicles = int.Parse(split[1]); break; case "CAPACITIES": instance.Capacities = int.Parse(split[1]); break; //case "DATA_SECTION": case "DEPOTS": for (int j = 0; j < instance.NumDepots; j++) { instance.Depots[j] = new Depot(); instance.Depots[j].depotID = int.Parse(lines[++i]); } break; case "DEMAND_SECTION": for (int j = 0; j < instance.NumVistis; j++) { instance.Clients[j] = new Client(); string[] clientsSplit = DVRPHelper.SplitText(lines[++i]); instance.Clients[j].visitID = int.Parse(clientsSplit[0]); instance.Clients[j].size = int.Parse(clientsSplit[1]); instance.ClientID[j] = j;//int.Parse(clientsSplit[0]); } break; case "LOCATION_COORD_SECTION": for (int j = 0; j < instance.NumLocations; j++) { instance.Locations[j] = new Location(); string[] locationsSplit = DVRPHelper.SplitText(lines[++i]); instance.Locations[j].locationID = int.Parse(locationsSplit[0]); instance.Locations[j].x = int.Parse(locationsSplit[1]); instance.Locations[j].y = int.Parse(locationsSplit[2]); } break; case "DEPOT_LOCATION_SECTION": for (int j = 0; j < instance.NumDepots; j++) { string[] depotLocationsSplit = DVRPHelper.SplitText(lines[++i]); int depotId = int.Parse(depotLocationsSplit[0]); instance.Depots.First(x => x.depotID == depotId).locationID = int.Parse(depotLocationsSplit[1]); } break; case "VISIT_LOCATION_SECTION": for (int j = 0; j < instance.NumVistis; j++) { string[] clientsSplit = DVRPHelper.SplitText(lines[++i]); int visitId = int.Parse(clientsSplit[0]); instance.Clients.First(x => x.visitID == visitId).locationID = int.Parse(clientsSplit[1]); } break; case "DURATION_SECTION": for (int j = 0; j < instance.NumVistis; j++) { string[] clientsSplit = DVRPHelper.SplitText(lines[++i]); int visitId = int.Parse(clientsSplit[0]); instance.Clients.First(x => x.visitID == visitId).unld = double.Parse(clientsSplit[1]); } break; case "DEPOT_TIME_WINDOW_SECTION": for (int j = 0; j < instance.NumDepots; j++) { string[] depotLocationsSplit = DVRPHelper.SplitText(lines[++i]); int depotId = int.Parse(depotLocationsSplit[0]); Depot d = instance.Depots.First(x => x.depotID == depotId); d.start = double.Parse(depotLocationsSplit[1]); d.end = double.Parse(depotLocationsSplit[2]); } break; //COMMENT: TIMESTEP: 7 case "TIME_AVAIL_SECTION": for (int j = 0; j < instance.NumVistis; j++) { string[] clientsSplit = DVRPHelper.SplitText(lines[++i]); int visitId = int.Parse(clientsSplit[0]); instance.Clients.First(x => x.visitID == visitId).time = double.Parse(clientsSplit[1]); } break; case "EOF": break; } } instance.distances = new double[instance.Locations.Length, instance.Locations.Length]; for (int j = 0; j < instance.Locations.Length; j++) { for (int k = 0; k < instance.Locations.Length; k++) { instance.distances[j, k] = DVRPHelper.Distance(instance.Locations[j], instance.Locations[k]); } } return(instance); }
public void FindCycle(int v, int k, double pathLen, double time, double capacity) { if (pathLen >= bestPathLen || time > dvrp.Depots[0].end) { return; } if (k == depth) { double distToDepot = DVRPHelper.Distance(act_cycle[act_cycle.Count - 1], act_cycle[0]); double timeToDepot = distToDepot / dvrp.Speed; if (pathLen + distToDepot < bestPathLen && time + timeToDepot < dvrp.Depots[0].end) { bestPathLen = pathLen + distToDepot; act_cycle.Add(dvrp.Locations[dvrp.Depots[0].locationID]); best_cycle = new List <Location>(act_cycle); arrivalTimes.Add(time + timeToDepot); bestArrivalsTimes = new List <double>(arrivalTimes); act_cycle.RemoveAt(act_cycle.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); } return; } for (int i = 0; i < clientsId.Length; i++) { if (!used[i]) { used[i] = true; if (capacity + dvrp.Clients[clientsId[i]].size > 0) { double dist = dvrp.distances[v, dvrp.Clients[clientsId[i]].locationID]; double t = dist / dvrp.Speed; double tWait = 0;//czas oczekiwania na przyjscie zgłoszenia if (dvrp.Clients[clientsId[i]].time < cutOff * dvrp.Depots[0].end && time < dvrp.Clients[clientsId[i]].time) { tWait = dvrp.Clients[clientsId[i]].time - time; } arrivalTimes.Add(time + t + tWait); act_cycle.Add(dvrp.Locations[dvrp.Clients[clientsId[i]].locationID]); FindCycle(dvrp.Locations[dvrp.Clients[clientsId[i]].locationID].locationID, k + 1, pathLen + dist, time + t + tWait + dvrp.Clients[clientsId[i]].unld, capacity + dvrp.Clients[clientsId[i]].size); act_cycle.RemoveAt(act_cycle.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); } else if (capacity + dvrp.Clients[clientsId[i]].size == 0) { double distToClient = dvrp.distances[v, dvrp.Clients[clientsId[i]].locationID]; double timeToClient = distToClient / dvrp.Speed; double tWait = 0;//czas oczekiwania na przyjscie zgłoszenia if (dvrp.Clients[clientsId[i]].time < cutOff * dvrp.Depots[0].end && time < dvrp.Clients[clientsId[i]].time) { tWait = dvrp.Clients[clientsId[i]].time - time; } arrivalTimes.Add(time + timeToClient + tWait); double distToDepot = dvrp.distances[dvrp.Clients[clientsId[i]].locationID, dvrp.Depots[0].locationID]; double timeToDepot = distToDepot / dvrp.Speed; arrivalTimes.Add(time + timeToClient + tWait + dvrp.Clients[clientsId[i]].unld + timeToDepot); act_cycle.Add(dvrp.Locations[dvrp.Clients[clientsId[i]].locationID]); act_cycle.Add(dvrp.Locations[dvrp.Depots[0].locationID]); depth++; FindCycle(0, k + 2, pathLen + distToClient + distToDepot, time + timeToClient + tWait + dvrp.Clients[clientsId[i]].unld + timeToDepot, dvrp.Capacities); depth--; act_cycle.RemoveAt(act_cycle.Count - 1); act_cycle.RemoveAt(act_cycle.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); } else { double distCD = 0; // distance from prev client to depot double distDC = 0; //disttance from depot to client if (act_cycle.Count > 0) { distCD = dvrp.distances[act_cycle[act_cycle.Count - 1].locationID, dvrp.Depots[0].locationID]; } distDC = dvrp.distances[dvrp.Depots[0].locationID, dvrp.Clients[clientsId[i]].locationID]; double tCD = distCD / dvrp.Speed; arrivalTimes.Add(time + tCD); double tDC = distDC / dvrp.Speed; double tWait = 0;//czas oczekiwania na przyjscie zgłoszenia if (dvrp.Clients[clientsId[i]].time < cutOff * dvrp.Depots[0].end && time < dvrp.Clients[clientsId[i]].time) { tWait = dvrp.Clients[clientsId[i]].time - time; } arrivalTimes.Add(time + tCD + tDC + tWait); act_cycle.Add(dvrp.Locations[dvrp.Depots[0].locationID]); depth++; act_cycle.Add(dvrp.Locations[dvrp.Clients[clientsId[i]].locationID]); FindCycle(dvrp.Clients[clientsId[i]].locationID, k + 2, pathLen + distCD + distDC, time + tCD + tDC + tWait, dvrp.Capacities + dvrp.Clients[clientsId[i]].size); depth--; act_cycle.RemoveAt(act_cycle.Count - 1); act_cycle.RemoveAt(act_cycle.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); arrivalTimes.RemoveAt(arrivalTimes.Count - 1); } used[i] = false; } } }