Skip to content

Nurse Scheduling API Reference

Data

Data model for NurseScheduling use case.

NurseSchedulingData

Bases: UcData

Data for the Nurse Scheduling Problem use case.

This class encapsulates all necessary information to define and solve a Nurse Scheduling problem instance. The unified formulation supports both 2-shift and 3-shift systems. Given a set of nurses and shifts, the problem creates rotating rosters that satisfy workforce requirements while respecting nurse preferences and day-off requests.

Attributes:

  • name (Literal['nurse_scheduling']) –

    A constant identifier for this data type, always set to "nurse_scheduling". Used for registration and type identification in the use case registry.

  • n_nurses (int) –

    Number of nurses available for scheduling.

  • n_shifts (int) –

    Number of shifts in the schedule.

  • workforce (NumPyArray) –

    Required workforce W(d) for each shift d. 1D float array of length n_shifts.

  • effort (NumPyArray) –

    Effort level E(n) for each nurse n. 1D float array of length n_nurses.

  • max_shifts (NumPyArray) –

    Maximum number of (weighted) shifts F(n) each nurse can work. 1D int array of length n_nurses.

  • shift_weight (NumPyArray) –

    Weight for each shift indicating how much it "counts" toward a nurse's maximum shift allowance (used in constraint C3). A weight of 2.0 means the shift counts double — e.g., a night shift with weight 2.0 uses two of a nurse's allowed shifts. 1D float array of length n_shifts.

  • day_off_priority (NumPyArray) –

    Priority matrix g(n,d) for day-off requests. 2D float array of shape (n_nurses, n_shifts). 0 = no request, higher = stronger request.

Examples:

Create a simple nurse scheduling instance:

>>> data = NurseSchedulingData(
...     n_nurses=3,
...     n_shifts=6,
...     workforce=np.array([2.0, 2.0, 2.0, 2.0, 2.0, 2.0]),
...     effort=np.array([1.0, 1.0, 1.0]),
...     max_shifts=np.array([3, 3, 3]),
...     shift_weight=np.array([1.0, 1.0, 1.0, 1.0, 1.0, 1.0]),
...     day_off_priority=np.zeros((3, 6)),
... )

plot(*, ax: Axes | None = None) -> Axes

Plot workforce requirements and shift weights.

Shows a bar chart of workforce requirements per shift with shift weights overlaid as a line.

Parameters:

  • ax (Axes | None, default: None ) –

    Matplotlib axes to draw on. Creates a new figure if None.

Returns:

  • Axes

    The axes with the plot.

to_string() -> str

Print the data.

Returns:

  • str

    String representation of the data.

from_values(n_nurses: int, n_shifts: int, workforce: np.ndarray | list[float], effort: np.ndarray | list[float], max_shifts: np.ndarray | list[int], shift_weight: np.ndarray | list[float], day_off_priority: np.ndarray | list[list[float]]) -> NurseSchedulingData staticmethod

Create a NurseSchedulingData instance from explicit values.

Parameters:

  • n_nurses (int) –

    Number of nurses available for scheduling.

  • n_shifts (int) –

    Number of shifts in the schedule.

  • workforce (ndarray | list[float]) –

    Required workforce W(d) for each shift d. 1D array of length n_shifts.

  • effort (ndarray | list[float]) –

    Effort level E(n) for each nurse n. 1D array of length n_nurses.

  • max_shifts (ndarray | list[int]) –

    Maximum number of (weighted) shifts F(n) each nurse can work. 1D array of length n_nurses.

  • shift_weight (ndarray | list[float]) –

    Weight for each shift. 1D array of length n_shifts.

  • day_off_priority (ndarray | list[list[float]]) –

    Priority matrix g(n,d) for day-off requests. 2D array of shape (n_nurses, n_shifts).

Returns:

generate_random(n_nurses: int = 10, n_shifts: int = 14, shift_system: str = 'two_shift', seed: int | None = None) -> NurseSchedulingData staticmethod

Generate a random Nurse Scheduling instance.

Parameters:

  • n_nurses (int, default: 10 ) –

    Number of nurses, by default 10.

  • n_shifts (int, default: 14 ) –

    Number of shifts, by default 14.

  • shift_system (str, default: 'two_shift' ) –

    Either "two_shift" or "three_shift", by default "two_shift". Controls how shift weights are generated.

  • seed (int | None, default: None ) –

    Random seed for reproducibility, by default None.

Returns:

Formulation

Formulation for NurseScheduling use case.

NurseSchedulingFormulation

Bases: UcFormulation[NurseSchedulingData, NurseSchedulingSolution]

Constraint-based formulation for Nurse Scheduling Problem.

This formulation uses Luna Model's constraint system to create rotating rosters that satisfy workforce requirements while respecting nurse preferences and day-off requests. Supports both 2-shift and 3-shift systems through unified shift weight parameters.

Mathematical Formulation

Given: - N nurses with effort levels E(n) and max shifts F(n) - D shifts with workforce requirements W(d) and weights - Day-off priority matrix g(n,d)

Decision Variables: q[n,d] in {0,1} for each nurse n and shift d q[n,d] = 1 if nurse n is assigned to shift d

Objective: minimize sum_{n,d} g(n,d) * q[n,d] (minimize scheduling nurses on their day-off requests)

Constraints: 1. No consecutive shifts: q[n,d] + q[n,d+1] <= 1 for each nurse n, shift d < D-1 2. Workforce requirement: sum_n E(n)q[n,d] >= W(d) for each shift d 3. Max shift count (weighted): sum_d shift_weight(d)q[n,d] <= F(n) for each nurse n

References
  • Nurse Scheduling Problem: https://en.wikipedia.org/wiki/Nurse_scheduling_problem

to_string(data: NurseSchedulingData) -> str staticmethod

Print the formulation.

Parameters:

Returns:

  • str

    String representation of the formulation.

formulate(data: NurseSchedulingData) -> Model staticmethod

Formulate the Nurse Scheduling Problem using constraint-based approach.

Creates a constraint-based formulation using binary decision variables for nurse-shift assignments with workforce, consecutive shift, and max shift count constraints.

Parameters:

Returns:

  • Model

    A Luna Model ready to be solved.

Raises:

  • EmptyDataError

    If there are no nurses or no shifts.

  • InvalidProblemStructureError

    If array dimensions do not match the declared sizes.

interpret(solution: Solution, data: NurseSchedulingData) -> NurseSchedulingSolution staticmethod

Extract solution from solver result.

Extracts the nurse-shift assignments from the solver solution and computes solution metrics including validity checks.

Parameters:

  • solution (Solution) –

    The solver solution containing variable assignments.

  • data (NurseSchedulingData) –

    The original Nurse Scheduling instance data.

Returns:

Raises:

Solution

Solution model for NurseScheduling use case.

NurseSchedulingSolution

Bases: UcSolution

Solution for the Nurse Scheduling Problem.

Attributes:

  • name (Literal['nurse_scheduling']) –

    Identifier for this solution type.

  • schedule (dict[int, list[int]]) –

    Maps nurse index to list of assigned shift indices.

  • n_shifts_assigned (int) –

    Total number of nurse-shift assignments.

  • is_valid (bool) –

    Whether constraints are satisfied (no consecutive shifts, workforce met).

plot(data: NurseSchedulingData | None = None, *, ax: Axes | None = None) -> Axes

Plot the nurse schedule as a grid.

Shows a heatmap where rows are nurses and columns are shifts. Assigned shifts are highlighted in color.

Parameters:

  • data (NurseSchedulingData | None, default: None ) –

    Problem data. When provided, workforce coverage info is shown.

  • ax (Axes | None, default: None ) –

    Matplotlib axes to draw on. Creates a new figure if None.

Returns:

  • Axes

    The axes with the plot.

to_string() -> str

Print the solution.

Returns:

  • str

    String representation of the solution.

Instance

Instance model for NurseScheduling use case.

NurseSchedulingInstance

Bases: UcInstance[NurseSchedulingData, NurseSchedulingFormulation, NurseSchedulingSolution]

Instance combining data and formulation for NurseScheduling.

Collection

Collection of NurseScheduling instances.

NurseSchedulingCollection

Bases: UcInstanceCollection[NurseSchedulingInstance]

Collection of Nurse Scheduling Problem instances.

This collection provides methods to generate benchmark instances with various characteristics for testing and evaluation, including random, two-shift, and three-shift system instances.

from_random(min_num_nurses: int, max_num_nurses: int, num_instances: int = 1, *, n_shifts: int = 14, shift_system: str = 'two_shift', seed: int | None = None) -> NurseSchedulingCollection classmethod

Generate random nurse scheduling instances.

Generates instances with varying nurse counts and random parameters.

Parameters:

  • min_num_nurses (int) –

    Minimum number of nurses per instance.

  • max_num_nurses (int) –

    Maximum number of nurses per instance.

  • num_instances (int, default: 1 ) –

    Number of instances per size, by default 1.

  • n_shifts (int, default: 14 ) –

    Number of shifts per instance, by default 14.

  • shift_system (str, default: 'two_shift' ) –

    Either "two_shift" or "three_shift", by default "two_shift".

  • seed (int | None, default: None ) –

    Random seed for reproducibility, by default None.

Returns:

Examples:

>>> collection = NurseSchedulingCollection.from_random(
...     min_num_nurses=5,
...     max_num_nurses=10,
...     num_instances=2,
...     seed=42,
... )

from_two_shift(min_num_nurses: int, max_num_nurses: int, num_instances: int = 1, *, n_shifts: int = 14, seed: int | None = None) -> NurseSchedulingCollection classmethod

Generate 2-shift system nurse scheduling instances.

Shift weights are based on h_1(n)*h_2(d) pattern where alternating shifts have different weights (e.g., day/night).

Parameters:

  • min_num_nurses (int) –

    Minimum number of nurses per instance.

  • max_num_nurses (int) –

    Maximum number of nurses per instance.

  • num_instances (int, default: 1 ) –

    Number of instances per size, by default 1.

  • n_shifts (int, default: 14 ) –

    Number of shifts per instance, by default 14.

  • seed (int | None, default: None ) –

    Random seed for reproducibility, by default None.

Returns:

Examples:

>>> collection = NurseSchedulingCollection.from_two_shift(
...     min_num_nurses=5,
...     max_num_nurses=10,
...     seed=42,
... )

from_three_shift(min_num_nurses: int, max_num_nurses: int, num_instances: int = 1, *, n_shifts: int = 21, seed: int | None = None) -> NurseSchedulingCollection classmethod

Generate 3-shift system nurse scheduling instances.

Shift weights are based on day_type*shift_type pattern: - shift_type: daytime=1.0, early_night=1.5, late_night=2.0 - day_type: weekday=1.0, weekend=2.0

Parameters:

  • min_num_nurses (int) –

    Minimum number of nurses per instance.

  • max_num_nurses (int) –

    Maximum number of nurses per instance.

  • num_instances (int, default: 1 ) –

    Number of instances per size, by default 1.

  • n_shifts (int, default: 21 ) –

    Number of shifts per instance, by default 21 (7 days * 3 shifts).

  • seed (int | None, default: None ) –

    Random seed for reproducibility, by default None.

Returns:

Examples:

>>> collection = NurseSchedulingCollection.from_three_shift(
...     min_num_nurses=8,
...     max_num_nurses=15,
...     seed=42,
... )