public void swapWards(TimeSlot t) { if (t.assignedWard != null && this.assignedWard != null) { //Swapping Timeslots this.assignedWard.timeslots.Add(t); this.assignedWard.timeslots.Remove(this); t.assignedWard.timeslots.Add(this); t.assignedWard.timeslots.Remove(t); //Swapping Wards Ward tempWard = t.assignedWard; t.assignedWard = this.assignedWard; this.assignedWard = tempWard; } else if(t.assignedWard == null) { t.assignedWard = this.assignedWard; t.assignedWard.timeslots.Add(t); this.assignedWard.timeslots.Remove(this); this.assignedWard = null; } else if (this.assignedWard == null) { this.assignedWard = t.assignedWard; this.assignedWard.timeslots.Add(this); t.assignedWard.timeslots.Remove(t); t.assignedWard = null; } }
//Adjusting the gaps internal void adjustGap(int minGap) { List<TimeSlot> sorted = this.timeslots.OrderBy(x => x.startTime).ToList(); TimeSpan smallestGap = new TimeSpan(); TimeSlot t1 = new TimeSlot(), t2 = new TimeSlot(); //Computing the smallest gap between dates as well as finding the timeslots around it for (int i = 0; i < sorted.Count - 1; i++) { //Computing the span TimeSpan currentGap = sorted[i + 1].startTime - sorted[i].startTime; if (i == 0) { smallestGap = currentGap; t2 = sorted[i + 1]; t1 = sorted[i]; continue; } if (currentGap < smallestGap) { smallestGap = currentGap; t2 = sorted[i + 1]; t1 = sorted[i]; } } //Swapping until it is in the threshhold int loops = 0; //int minGap = 40; while (true) { //Swap slots with another ward List<TimeSlot> tempList = new List<TimeSlot>(t1.sectionList); tempList.Shuffle(); //Going through each TimeSlot in the same period and looking for the best fit. //double bestFit; //TimeSlot bestFitSlot; foreach (TimeSlot tOther in tempList) { Ward tOtherWard = tOther.assignedWard; t1.swapWards(tOther); //double currentMinSpacing = this.minTimeslotSpacing; if ((tOtherWard == null || tOtherWard.minTimeslotSpacing > minGap) && this.minTimeslotSpacing > minGap) { break; } else t1.swapWards(tOther); } if (this.minTimeslotSpacing < minGap) minGap--; else break; loops++; } }
/// <summary> /// Generating the available timeslots for the year /// </summary> /// <param name="begin"></param> /// <param name="end"></param> private void generateTimeSlots(DateTime begin, DateTime end) { //Refreshing the interval timeslots dictionaries timeslots = new List<TimeSlot>(); freetimeslots = new Queue<TimeSlot>(); takentimeslots = new List<TimeSlot>(); weekendtimeslots = new List<TimeSlot>(); weekdaytimeslots = new List<TimeSlot>(); intervalTimeSlots = new Dictionary<int, List<TimeSlot>>(); weekdayIntervalTimeSlots = new Dictionary<int, List<TimeSlot>>(); weekendIntervalTimeSlots = new Dictionary<int, List<TimeSlot>>(); // 1) Find all days that aren't blacked out List<DateTime> availableDays = new List<DateTime>(); for (DateTime date = begin; date <= end; date = date.AddDays(1)) { if (date.DayOfWeek == System.DayOfWeek.Monday || date.DayOfWeek == System.DayOfWeek.Sunday || blackoutDates.Contains(date)) continue; availableDays.Add(date); } // 2) Divide up available days into equal intervals int totalDays = availableDays.Count; decimal decimalInterval = totalDays / this.numericUpDown1.Value; int intervalLength = (int)Math.Ceiling(decimalInterval); int currentSpan = 0; for (int i = 0; i < this.numericUpDown1.Value; i++) { //Adding a list for each timeslot this.intervalTimeSlots.Add(i, new List<TimeSlot>()); this.weekdayIntervalTimeSlots.Add(i, new List<TimeSlot>()); this.weekendIntervalTimeSlots.Add(i, new List<TimeSlot>()); } // 3) Generate Timeslots for each day //Looping through each date in the range for (int i = 0; i < availableDays.Count; i++ ){ DateTime date = availableDays[i]; //Determining which span of the year the date belongs to if (i % intervalLength == 0 && i > 0 && i < (intervalLength * this.numericUpDown1.Value)) currentSpan++; //Adding TimeSlots for weeks of the days if (date.DayOfWeek != System.DayOfWeek.Saturday) { foreach (TimeSpan j in weekdayStartHours) { //Adding Weekday Slots TimeSlot ts = new TimeSlot(new DateTime(date.Year, date.Month, date.Day, j.Hours, j.Minutes, 0)); timeslots.Add(ts); weekdaytimeslots.Add(ts); weekdayIntervalTimeSlots[currentSpan].Add(ts); intervalTimeSlots[currentSpan].Add(ts); //ts.sectionList = intervalTimeSlots[currentSpan]; ts.sectionList = weekdayIntervalTimeSlots[currentSpan]; } } else { //Adding Saturdays foreach (TimeSpan j in weekendStartHours) { //Adding Weekend Slots TimeSlot ts = new TimeSlot(new DateTime(date.Year, date.Month, date.Day, j.Hours, j.Minutes, 0)); timeslots.Add(ts); weekendtimeslots.Add(ts); weekendIntervalTimeSlots[currentSpan].Add(ts); intervalTimeSlots[currentSpan].Add(ts); //ts.sectionList = intervalTimeSlots[currentSpan]; ts.sectionList = weekendIntervalTimeSlots[currentSpan]; } } } List<TimeSlot> asdf = this.timeslots.FindAll(x => x.sectionList == null); //Adding interval text to the data table this.listView1.Items.Clear(); int allWeekday = 0; int allWeekdaysNeeded = 0; int allSaturdays = 0; int allSaturdaysNeeded = 0; int allDays = 0; int allDaysNeeded = 0; for (int i = 0; i < intervalTimeSlots.Count; i++) { ListViewItem lvi = new ListViewItem("Interval " + i); lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, weekdayIntervalTimeSlots[i].Count.ToString())); int neededWeekdays = (int)(this.numericUpDownWeekdays.Value*this.wards.Count/this.numericUpDown1.Value); lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, neededWeekdays.ToString() )); allWeekday += weekdayIntervalTimeSlots[i].Count; allWeekdaysNeeded += neededWeekdays; lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, weekendIntervalTimeSlots[i].Count.ToString())); int neededSaturdays = (int)(this.numericUpDownWeekends.Value * this.wards.Count / this.numericUpDown1.Value); lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, neededSaturdays.ToString() )); allSaturdays += weekendIntervalTimeSlots[i].Count; allSaturdaysNeeded += neededSaturdays; int neededTotal = (int)((this.numericUpDownWeekdays.Value + this.numericUpDownWeekends.Value) * this.wards.Count / this.numericUpDown1.Value); lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, intervalTimeSlots[i].Count.ToString())); lvi.SubItems.Add(new ListViewItem.ListViewSubItem(lvi, neededTotal.ToString())); allDays += intervalTimeSlots[i].Count; allDaysNeeded += neededTotal; listView1.Items.Add(lvi); } //All intervals ListViewItem tlvi = new ListViewItem("Whole Year"); tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allWeekday.ToString())); //All Weekdays tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allWeekdaysNeeded.ToString())); //All Weekdays Needed tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allSaturdays.ToString())); //All Saturdays tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allSaturdaysNeeded.ToString())); //All Saturdays Needed tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allDays.ToString())); //Total tlvi.SubItems.Add(new ListViewItem.ListViewSubItem(tlvi, allDaysNeeded.ToString())); //Total Needed listView1.Items.Add(tlvi); }