Reputation: 39
I am writing a C# program to handle scheduling. Now each employee needs the ability have limitations on their schedule for ex:
Sally can only work Monday, Wednesday, Friday from 9am-3pm
Billy can only work Tuesday, Thursday, Sunday from 5pm-9pm
Sally can only work Monday, Wednesday, Friday from 9am-3pm until so and so date and then she can work a different set of times and days.
These are some examples of limitations that I need to apply to each employee object. What I wanted were some suggestions on how to architect this as efficiently and generically as as possible. Obviously I am going to have to be able to access this data and be able to apply these limitations. For example when the manger is trying to make the schedule he needs to able to see that when he schedules Sally on Tuesday at 4 their is an issue. Also how should I store this data of each employee?
Upvotes: 2
Views: 1656
Reputation: 13384
I would go with Rules
using the strategy pattern.
public interface Rule
{
bool Satisfies(Employee employee);
}
public class ScheduleRule : Rule
{
ScheduleRule(Schedule schedule)
{ ... }
bool Satisfies(Employee employee)
{
// Ensure the employee is available
}
}
public class HolidayRule : Rule
{
HolidayRule(Datetime date)
{ ... }
bool Satisfies(Employee employee)
{
// Checks if the employee as volunteered for this holiday
}
}
This pattern allows for easy extensibility and maintainability.
The availibility information (and other rule-related information) can be kept with the employee (see Mike Jacob's answer). It can however be stored with the employee or in a seperate table.
You can also keep this availability information apart from the employee if you expect a large amount of information related to rules. In this case, Rules
could target another class:
...
bool Satisfies(RuleInfo info)
...
Upvotes: 1
Reputation: 509
something like this:
public class Employee
{
public string Name { get; set; }
// other important info
private List<WorkTime> _availability = new List<WorkTime>();
public List<WorkTime> Availability
{
get { return _availability; }
internal set { _availability = value; }
}
}
public class WorkTime
{
public DayOfWeek Day { get; private set; }
public int StartHour { get; private set; }
public int EndHour { get; private set; }
public WorkTime(DayOfWeek day, int startHour, int endHour)
{
// validation here (e.g. day and time range during store hours, start<end, etc.)
Day = day;
StartHour = startHour;
EndHour = endHour;
}
}
and use LINQ (or foreach) to query across an employee collection, and into each employee's Availability to find someone with hours to meet some shift.
Might also be useful to create some utility function (extensions) for comparing WorkTime objects based on your business rules (e.g. IsAvailable compares two WorkTime objects and returns true if it's the same DoW and at least 4 hours overlap)
and you'll likely be storing this in a database, so model the tables with fields like the properties in the classes.
Upvotes: 1
Reputation: 1001
I've done something similar to this and what i've done is created a common interface and then created separate implementations for different scenarios. The interface might have a check IsInSchedule(dateTime). Then you can create different implementations as needed.
Upvotes: 0
Reputation: 19624
This is analogous to a graph-matching problem, and can also be modeled as a Constraint Satisfaction Problem. You may find NSolver helpful, or Cassowary.Net
Upvotes: 0
Reputation: 6612
"architect this as efficiently and generically as as possible"
These aren't mutually exclusive, per-se, however efficient and generic is really hard to pull off, especially on a scheduling system. Scheduling is a non-trivial problem.
Your question would probably better be stated as "What books should I read to get started on this?" and/or make this a community wiki.
Upvotes: 0
Reputation: 47726
I would suggest giving the ability to store 'time off' as specific dates with time ranges or as a pattern. I have worked on a couple of scheduling systems that had very complex ways of dealing with union rules and employee availablity and this is how we handled it.
Either employee says I want day X from y to z off which is easy to check against or they could define patterns that they wanted or didn't want (eg. I dont want to work fridays) and then when scheduling you could check to see if applying them to a specific shift broke a set rule (day off) or did/didn't match a specific pattern.
Also how should I store this data of each employee?
Have a table for storing employee's specific exceptions. I want day X from y to z off. You have an employee a date and a time span. Pretty simple.
As for the patterns you will need to come up with some type of schema. And have types or something.
So you could have a type like 'weekly off pattern' that would store full days off for a week which could be stored as a simple string representing the days off: 1000001. Assuming the first bit is sunday, this would represent wanting weekends off. You could then store the pattern as string or something and then based on the defined type you would know how to deal with the string.
It can be a very complex or simple problem, it just depends how much customization you need to allow for. Hopefully this gives you enough ideas to get you started.
Automatic schedule generation is A LOT more complicated depending on the exceptions/rules you need to support.
Upvotes: 0