blackopsrepl's picture
feat(app): add hospital scheduling application
b7e7f16
use chrono::Weekday;
use super::vocabulary::*;
/// Reusable calendar patterns for demand templates.
#[derive(Clone, Copy)]
pub(super) enum WeekPattern {
Weekdays,
Weekends,
Daily,
MonWedFri,
Saturday,
Sunday,
}
#[derive(Clone, Copy)]
pub(super) struct DemandRule {
pub(super) location: &'static str,
pub(super) start_hour: u32,
pub(super) required_skill: &'static str,
pattern: WeekPattern,
pub(super) count: usize,
}
// This is the published demand template for the 28-day benchmark. Each rule
// says "on matching weekdays, create `count` eight-hour shifts of this shape".
pub(super) const DEMAND_RULES: &[DemandRule] = &[
DemandRule {
location: "Ambulatory care",
start_hour: 6,
required_skill: AMBULATORY_DOCTOR,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Ambulatory care",
start_hour: 14,
required_skill: AMBULATORY_NURSE,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Ambulatory care",
start_hour: 6,
required_skill: AMBULATORY_DOCTOR,
pattern: WeekPattern::Weekends,
count: 1,
},
DemandRule {
location: "Ambulatory care",
start_hour: 14,
required_skill: AMBULATORY_NURSE,
pattern: WeekPattern::Weekends,
count: 2,
},
DemandRule {
location: "Neurology",
start_hour: 6,
required_skill: NEUROLOGY_DOCTOR,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Neurology",
start_hour: 14,
required_skill: NEUROLOGY_NURSE,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Neurology",
start_hour: 6,
required_skill: NEUROLOGY_DOCTOR,
pattern: WeekPattern::Weekends,
count: 1,
},
DemandRule {
location: "Neurology",
start_hour: 14,
required_skill: NEUROLOGY_NURSE,
pattern: WeekPattern::Weekends,
count: 1,
},
DemandRule {
location: "Neurology",
start_hour: 22,
required_skill: CARDIOLOGY,
pattern: WeekPattern::MonWedFri,
count: 1,
},
DemandRule {
location: "Critical care",
start_hour: 6,
required_skill: CRITICAL_DOCTOR,
pattern: WeekPattern::Daily,
count: 2,
},
DemandRule {
location: "Critical care",
start_hour: 14,
required_skill: CRITICAL_NURSE,
pattern: WeekPattern::Daily,
count: 2,
},
DemandRule {
location: "Critical care",
start_hour: 22,
required_skill: CRITICAL_DOCTOR,
pattern: WeekPattern::Daily,
count: 1,
},
DemandRule {
location: "Critical care",
start_hour: 9,
required_skill: CRITICAL_NURSE,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Pediatric care",
start_hour: 6,
required_skill: PEDIATRIC_DOCTOR,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Pediatric care",
start_hour: 14,
required_skill: PEDIATRIC_NURSE,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Pediatric care",
start_hour: 6,
required_skill: PEDIATRIC_DOCTOR,
pattern: WeekPattern::Weekends,
count: 1,
},
DemandRule {
location: "Pediatric care",
start_hour: 14,
required_skill: PEDIATRIC_NURSE,
pattern: WeekPattern::Weekends,
count: 2,
},
DemandRule {
location: "Surgery",
start_hour: 6,
required_skill: SURGERY_DOCTOR,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Surgery",
start_hour: 14,
required_skill: ANAESTHETICS,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Surgery",
start_hour: 22,
required_skill: SURGERY_NURSE,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 6,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Radiology",
start_hour: 9,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 14,
required_skill: RADIOLOGY_NURSE,
pattern: WeekPattern::Weekdays,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 22,
required_skill: RADIOLOGY_CALL,
pattern: WeekPattern::MonWedFri,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 6,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Saturday,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 9,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Saturday,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 14,
required_skill: RADIOLOGY_NURSE,
pattern: WeekPattern::Saturday,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 6,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Sunday,
count: 1,
},
DemandRule {
location: "Radiology",
start_hour: 9,
required_skill: RADIOLOGY_DAY,
pattern: WeekPattern::Sunday,
count: 1,
},
DemandRule {
location: "Outpatient",
start_hour: 6,
required_skill: OUTPATIENT_NURSE,
pattern: WeekPattern::Weekdays,
count: 2,
},
DemandRule {
location: "Outpatient",
start_hour: 14,
required_skill: OUTPATIENT_DOCTOR,
pattern: WeekPattern::Weekdays,
count: 1,
},
];
impl DemandRule {
/// Expands a rule into the number of shifts it contributes on a specific weekday.
pub(super) fn count_for_date(&self, weekday: Weekday) -> usize {
if self.pattern.matches(weekday) {
self.count
} else {
0
}
}
}
impl WeekPattern {
/// Returns whether the abstract pattern includes the given weekday.
fn matches(self, weekday: Weekday) -> bool {
match self {
WeekPattern::Weekdays => matches!(
weekday,
Weekday::Mon | Weekday::Tue | Weekday::Wed | Weekday::Thu | Weekday::Fri
),
WeekPattern::Weekends => matches!(weekday, Weekday::Sat | Weekday::Sun),
WeekPattern::Daily => true,
WeekPattern::MonWedFri => matches!(weekday, Weekday::Mon | Weekday::Wed | Weekday::Fri),
WeekPattern::Saturday => weekday == Weekday::Sat,
WeekPattern::Sunday => weekday == Weekday::Sun,
}
}
}