private static void removeByShiftRotation(Dictionary <string, Worker> workers, int day, Shift shift) { if (day == 0) { return; } List <string> toRemove = new List <string>(); foreach (Worker w in workers.Values) { if (w.Assignments.ContainsKey(day - 1)) { Assignment prevDayAssignment = w.Assignments[day - 1]; if (prevDayAssignment.Shift.ProhibitsFollowingShifts.Contains(shift.ID)) { toRemove.Add(w.ID); } } } foreach (string wr in toRemove) { Console.WriteLine("\t\t\tRemoving " + wr); workers.Remove(wr); } }
public static void TryFill() { foreach (Worker w in Workers.Values) { int sum = 0; int count = 0; foreach (string shiftID in w.MaxShifts.Keys) { count++; sum += Shifts[shiftID].Length; } int avgShiftLength = sum / count; int moreMinutes = w.MinTotalMinutes - w.WorkedMinutes + (w.MaxTotalMinutes - w.MinTotalMinutes) / 2; int moreShifts = moreMinutes / avgShiftLength; int moreGiven = 0; for (int day = 0; day < Days; day++) { if (w.WorkedMinutes >= w.MinTotalMinutes) { break; } if (w.DaysOff.Contains(day)) { continue; } if (!w.Assignments.ContainsKey(day)) { int holeLeftLength = 0; int dayBack = 1; while (true) { if (w.DaysOff.Contains(day - dayBack)) { break; } if (w.Assignments.ContainsKey(day - dayBack) || day - dayBack < 1) { break; } else { holeLeftLength++; } dayBack++; } int holeRightLength = 0; int dayForward = 1; while (true) { if (w.DaysOff.Contains(day + dayForward)) { break; } if (w.Assignments.ContainsKey(day + dayForward) || day + dayForward > Days - 1) { break; } else { holeRightLength++; } dayForward++; } int holeLength = holeLeftLength + holeRightLength + 1; int sectionLeftLength = 0; dayBack = holeLeftLength + 1; while (true) { if (w.DaysOff.Contains(day - dayBack)) { break; } if (!w.Assignments.ContainsKey(day - dayBack) || day - dayBack < 0) { break; } else { sectionLeftLength++; } dayBack++; } int sectionRightLength = 0; dayForward = holeRightLength + 1; while (true) { if (w.DaysOff.Contains(day + dayForward)) { break; } if (!w.Assignments.ContainsKey(day + dayForward) || day + dayForward > Days) { break; } else { sectionRightLength++; } dayForward++; } if (sectionLeftLength + holeLength + sectionRightLength <= w.MaxConsecutiveShifts) { List <Assignment> aas = new List <Assignment>(); int mw = 0; int cnt = 0; for (int i = day - holeLeftLength; i < day - holeLeftLength + holeLength; i++) { Assignment a = new Assignment(); a.Day = i; a.Worker = w; a.Shift = null; if (w.ShiftOnRequests.ContainsKey(i)) { a.Shift = Shifts[w.ShiftOnRequests[i].ID]; } else { foreach (string shiftID in w.MaxShifts.Keys) { if (w.WorkedShiftsByType(shiftID) + 1 >= w.MaxShifts[shiftID]) { continue; } else { Shift prevShift = null; if (aas.Count > 0) { prevShift = aas.Last().Shift; } else { if (w.Assignments.ContainsKey(day - holeLeftLength - 1)) { prevShift = w.Assignments[day - holeLeftLength - 1].Shift; } } if (prevShift != null && !Shifts[prevShift.ID].ProhibitsFollowingShifts.Contains(shiftID)) { if (w.Assignments.ContainsKey(day + holeRightLength + 1) && !w.Assignments[day + holeRightLength + 1].Shift.ProhibitsFollowingShifts.Contains(shiftID)) { a.Shift = Shifts[shiftID]; break; } else if (!w.Assignments.ContainsKey(day + holeRightLength + 1)) { a.Shift = Shifts[shiftID]; break; } } } } } if (a.Shift != null) { cnt++; aas.Add(a); bool isWeekend = false; if ((i + 1) % 7 == 0 || (i + 2) % 7 == 0) { mw++; } moreGiven++; } } if (w.WorkedWeekends + mw > w.MaxWeekends) { continue; } else { foreach (Assignment a in aas) { w.Assignments[a.Day] = a; } } } } } } }
public static void ExpandRight() { foreach (Worker w in Workers.Values) { for (int day = 0; day < Days; day++) { if (!w.Assignments.ContainsKey(day)) { continue; } Shift lastShift = w.Assignments[day].Shift; int numConsecutive = 1; for (int d = day - 1; d >= 0; d--) { if (w.Assignments.ContainsKey(d)) { numConsecutive++; } else { break; } } int numFree = 0; while (true) { Console.WriteLine(day + " " + numFree); if (day + numFree + 1 >= Days) { break; } if (w.Assignments.ContainsKey(day + numFree + 1)) { break; } else { numFree++; } } for (int d = day + 1; d < day + 1 + numFree - w.MinConsecutiveDaysOff; d++) { if ((d + 1) % 7 == 0 || (d + 2) % 7 == 0) { break; } if (w.DaysOff.Contains(d)) { break; } if (numConsecutive >= w.MaxConsecutiveShifts) { break; } if (w.WorkedShiftsByType(lastShift.ID) >= w.MaxShifts[lastShift.ID]) { break; } if (w.WorkedMinutes + lastShift.Length > w.MaxTotalMinutes) { break; } Assignment a = new Assignment(); a.Day = d; a.Worker = w; a.Shift = lastShift; w.Assignments[d] = a; numConsecutive++; } } } }
public static void ExpandLeft() { foreach (Worker w in Workers.Values) { for (int day = 1; day < Days; day++) { if (w.Assignments.ContainsKey(day) && !w.Assignments.ContainsKey(day - 1)) { Shift nextShift = w.Assignments[day].Shift; int back = 0; while (true) { if (day - back - 1 < 0) { break; } if (w.Assignments.ContainsKey(day - back - 1)) { break; } else { back++; } } int sectionLength = 0; while (true) { if (!w.Assignments.ContainsKey(day + sectionLength)) { break; } else { sectionLength++; } } if (sectionLength >= w.MaxConsecutiveShifts) { continue; } if (back <= w.MinConsecutiveDaysOff) { continue; } for (int d = 1; d < back - w.MinConsecutiveDaysOff; d++) { if (w.DaysOff.Contains(day - d)) { break; } Shift possibleShift = null; foreach (Shift s in Shifts.Values) { if (ShiftCanBeBefore(s.ID, nextShift.ID)) { possibleShift = s; break; } } possibleShift = nextShift; if (possibleShift != null) { if (w.WorkedMinutes + possibleShift.Length > w.MaxTotalMinutes) { break; } Assignment a = new Assignment(); a.Day = day - d; a.Shift = possibleShift; a.Worker = w; w.Assignments[day - d] = a; nextShift = possibleShift; Console.WriteLine("Left"); Console.WriteLine(w.ID); Console.WriteLine(day - d); } } } } } }
private static void removeByMaxTotalMinutes(Dictionary <string, Worker> workers, Shift shift) { List <string> toRemove = new List <string>(); foreach (Worker w in workers.Values) { if (w.WorkedMinutes + shift.Length > w.MaxTotalMinutes) { toRemove.Add(w.ID); } } foreach (string wr in toRemove) { Console.WriteLine("\t\t\tRemoving " + wr); workers.Remove(wr); } }