public List <MultiResult> Run() { StartLogging(); if (FixedTimeSlotAssignments != null) { Console.WriteLine("Fixing timeslots"); _model.SetAndFixSolution(FixedTimeSlotAssignments); } double minCost; int maxSoftConsViol; int minSoftConsViol; double maxCost; int costBound; int softObjBound; CalculateCornerPoints(_multiResults, out minCost, out maxCost, out maxSoftConsViol, out minSoftConsViol, out costBound, out softObjBound); Console.WriteLine($"Slope between corners: {(maxCost-minCost)/(maxSoftConsViol-minSoftConsViol) : #.##}\nPenalty: {_model.ModelParameters.ConstraintPenalty}"); var pareto = GetParetoPoints(_multiResults); if (Math.Abs(minCost - maxCost) < 0.05) { Console.WriteLine("Only one solution found. Returning"); return(pareto); } if (UseEpsilonMethod) { RunEpsilonMethod(minSoftConsViol, maxSoftConsViol, minCost, maxCost); } else { RunWieghtedSumMetod(minSoftConsViol, maxSoftConsViol, minCost, maxCost); } _stopwatch.Stop(); //todo: refactor this in to its own function. Console.WriteLine($"Elapsed time: {_stopwatch.Elapsed} -- {_stopwatch.ElapsedMilliseconds}ms"); pareto = GetParetoPoints(_multiResults); Console.WriteLine($"\nBounds:\nCost: {costBound}\nSoftObj: {softObjBound}\n"); DisplaySolutions(pareto); DisplayRoomProfiles(pareto); DisplayTimeSlots(pareto); DisplayChanges(pareto); return(pareto); }
public Solution SolveStageII() { var model = new CCTModel(data, formulation, new CCTModel.MIPModelParameters() { UseStageIandII = true, }); model.SetAndFixSolution(_solution._assignments.ToList()); //model.MipStart(_solution._assignments.ToList()); model.Optimize(1200); _solution.SetAssignments(model.GetAssignments()); return(_solution); }
public void TestSolutionread() { var data = Data.ReadXml(dataPath + ITC_Comp01, "120", "4"); var formulation = ProblemFormulation.UD2; var sol = new Solution(data, formulation); sol.Read(dataPath + @"ITC2007\sol\comp01-UD2.sol"); sol.AnalyzeSolution(); Assert.AreEqual(0, sol.UnscheduledLectures); var model = new CCTModel(data, ProblemFormulation.UD2); model.SetAndFixSolution(sol._assignments.ToList()); model.Optimize(); Assert.AreEqual(5, model.Objective); }
public void TopSolutionsAnalysis(string filename) { var name = Path.GetFileNameWithoutExtension(filename); var data = Data.ReadXml(dataPath + filename, "120", "4"); var formulation = ProblemFormulation.UD2NoOverbook; var courestime = new Dictionary <Course, Dictionary <TimeSlot, int> >(); var penaltyforcourse = new Dictionary <Course, int>(); foreach (var course in data.Courses) { courestime.Add(course, new Dictionary <TimeSlot, int>()); foreach (var timeSlot in data.TimeSlots) { courestime[course].Add(timeSlot, 0); } penaltyforcourse[course] = 0; } var bestsol = new List <Assignment>(); var penMWD = new List <int>(); var penCC = new List <int>(); for (var i = 0; i < 10; i++) { var sol = new Solution(data, formulation); sol.Read(dataPath + @"ITC2007\sol\" + name + "-UD2-" + i + ".sol"); sol.AnalyzeSolution(); foreach (var assignment in sol._assignments) { courestime[assignment.Course][assignment.TimeSlot]++; } foreach (var course in data.Courses) { penaltyforcourse[course] += sol.PenaltyForCourse[course]; } penMWD.Add((int)sol.MinimumWorkingDays); penCC.Add((int)sol.CurriculumCompactness); if (i == 0) { bestsol = sol._assignments.ToList(); } } const int minhint = 7; var maxhint = 7; var noise = 0.5; const bool fixhints = true; var random = new Random(62); foreach (var course in data.Courses) { foreach (var ts in data.TimeSlots) { // if (random.Next(10) < courestime[course][ts]) courestime[course][ts] = 1; // else courestime[course][ts] = 0; if (courestime[course][ts] < minhint) { courestime[course][ts] = 0; } if (courestime[course][ts] > maxhint) { courestime[course][ts] = 0; } //result should be made to double. // if(courestime[course][ts] > 0) courestime[course][ts] += random.Next(-3,3); //courestime[course][ts] *= 1 + (int) Math.Round(noise*(2*random.NextDouble()-1)); } } var hints = courestime.SelectMany(c => c.Value.Where(cv => cv.Value > 0).Select(cv => Tuple.Create(c.Key, cv.Key, cv.Value))).ToList(); var currtime = new Dictionary <Curriculum, Dictionary <TimeSlot, int> >(); foreach (var curr in data.Curricula) { currtime.Add(curr, new Dictionary <TimeSlot, int>()); foreach (var timeSlot in data.TimeSlots) { currtime[curr].Add(timeSlot, courestime.Where(c => curr.Courses.Contains(c.Key)).Sum(kv => kv.Value[timeSlot])); } } var chints = currtime.SelectMany(c => c.Value.Select(cv => Tuple.Create(c.Key, cv.Key, cv.Value))).ToList(); Console.WriteLine($"Timeslots: {data.TimeSlots.Count}"); Console.WriteLine($"MWD: avg: {penMWD.Average()} - {string.Join(", ", penMWD)} "); Console.WriteLine($"CC: avg: {penCC.Average()} - {string.Join(", ", penCC)} "); foreach (var course in data.Courses.OrderByDescending(c => penaltyforcourse[c])) { Console.WriteLine($"\nCourse: {course}\n" + $"Size: {course.NumberOfStudents}\n" + $"Lectures: {course.Lectures}\n" + $"MWD: {course.MinimumWorkingDays}\n" + $"TSAvaialble:{data.TimeSlots.Count - course.UnavailableTimeSlots.Count}\n" + $"Unavail: {string.Join(",", course.UnavailableTimeSlots)}\n" + $"TotalPenalty: {penaltyforcourse[course]}"); foreach (var valuePair in courestime[course].Where(kv => kv.Value > 0).OrderByDescending(kv => kv.Value)) { Console.WriteLine(valuePair.Key + ": " + valuePair.Value); } } Console.WriteLine("\n\nBy prio: "); foreach (var hint in hints.Where(h => h.Item3 > 0).OrderByDescending(h => h.Item3)) { Console.WriteLine(hint.Item1.ID + "_" + hint.Item2 + ": " + hint.Item3); } Console.WriteLine("\n\nHistogram: "); Console.WriteLine("total lectures: " + data.Courses.Sum(c => c.Lectures)); for (var i = 1; i <= 10; i++) { Console.WriteLine($"{i}\t{hints.Count(h => h.Item3 == i)}"); } Console.WriteLine("Unavailabilites\tSame"); foreach (var course in data.Courses) { Console.WriteLine($"{course.UnavailableTimeSlots.Count}\t{(double) courestime[course].Sum(t => t.Value)/course.Lectures : 0.00}"); } Console.WriteLine("Penal\tSame"); foreach (var course in data.Courses) { Console.WriteLine($"{penaltyforcourse[course]}\t{(double) courestime[course].Sum(t => t.Value)/course.Lectures : 0.00}"); } Console.WriteLine("Size\tSame"); foreach (var course in data.Courses) { Console.WriteLine($"{course.NumberOfStudents}\t{(double) courestime[course].Sum(t => t.Value)/course.Lectures : 0.00}"); } // return; //Console.WriteLine("\n\nCurriculumPatterns"); //foreach (var hint in chints.Where(h => h.Item3 > 0).OrderByDescending(h => h.Item3)) //{ // Console.WriteLine(hint.Item1.ID + "_" + hint.Item2 + ": " + hint.Item3); //} //Console.WriteLine("\n\nHistogram: "); //Console.WriteLine("total curr_lectures: " + data.Curricula.Sum(c => c.Lectures)); //for (var i = 1; i <= 10; i++) //{ // Console.WriteLine($"{i}\t{chints.Count(h => h.Item3 == i)}"); //} var ModelParameters = new CCTModel.MIPModelParameters() { UseStageIandII = false, TuneGurobi = true, UseHallsConditions = true, UseRoomHallConditions = true, // Seed = seeds[i], }; var model = new CCTModel(data, formulation, ModelParameters); // model.SetMipHints(chints); Console.WriteLine($"Adding {hints.Count} hints. Total letures: {data.Courses.Sum(c => c.Lectures)} ({(double) hints.Count / data.Courses.Sum(c => c.Lectures) :0.00%})"); model.SetMipHints(hints, fixhints); // model.MipStart(bestsol); var r = model.Optimize(300); // model.Optimize(60*60*3); var ass = model.GetAssignments(); var finalsol = new Solution(data, formulation); finalsol.SetAssignments(ass); finalsol.Save(@"C:\temp\finalsolStageI_" + name + ".sol"); var ModelParameters2 = new CCTModel.MIPModelParameters() { UseStageIandII = true, TuneGurobi = true, UseHallsConditions = true, UseRoomHallConditions = true, // Seed = seeds[i], }; var model2 = new CCTModel(data, formulation, ModelParameters2); model2.SetAndFixSolution(ass); model2.Optimize(300); ass = model2.GetAssignments(); finalsol.SetAssignments(ass); finalsol.Save(@"C:\temp\finalsolStageII_" + name + ".sol"); }