Design a Driver Payroll System
RipplingSoftware Engineer · Technical ScreenLast updated
Design an in-memory driver payroll system that records time-stamped earnings and supports efficient range queries for both individual drivers and company-wide aggregates.
Problem Statement
Design an in-memory payroll tracking system for a ride-sharing company. The system tracks earnings generated by drivers over time and allows querying individual driver earnings as well as total company payroll across specified time windows.
Implement the DriverPayroll class:
__init__(): Initializes the payroll system.record_earning(driver_id: str, timestamp: int, amount: int) -> None: Records an earningamount(in cents) fordriver_idat a giventimestamp. Calls torecord_earningare guaranteed to arrive in non-decreasing order oftimestampglobally.get_driver_earnings(driver_id: str, start_time: int, end_time: int) -> int: Returns the total earnings fordriver_idbetweenstart_timeandend_time, inclusive. If the driver has no earnings in this range or does not exist, return0.get_total_payroll(start_time: int, end_time: int) -> int: Returns the sum of earnings across all drivers betweenstart_timeandend_time, inclusive.
Example
payroll = DriverPayroll()
payroll.record_earning("driver_1", 10, 500) # $5.00 for driver_1 at t=10
payroll.record_earning("driver_2", 15, 750) # $7.50 for driver_2 at t=15
payroll.record_earning("driver_1", 20, 300) # $3.00 for driver_1 at t=20
payroll.record_earning("driver_1", 25, 200) # $2.00 for driver_1 at t=25
# Driver 1 earnings between t=10 and t=20 (500 + 300)
assert payroll.get_driver_earnings("driver_1", 10, 20) == 800
# Total payroll between t=12 and t=22 (750 + 300)
assert payroll.get_total_payroll(12, 22) == 1050
# Query with no earnings
assert payroll.get_driver_earnings("driver_2", 16, 30) == 0
assert payroll.get_driver_earnings("driver_3", 0, 100) == 0
Constraints
1 <= len(driver_id) <= 321 <= timestamp <= 10^91 <= amount <= 10^60 <= start_time <= end_time <= 10^9- At most
2 * 10^5total calls across all methods. - Multiple earnings may be recorded at the exact same timestamp (for the same or different drivers).
Edge Cases to Consider
- Querying a
driver_idthat was never recorded. - Time windows that cover no events or encompass all recorded events.
- Multiple earnings occurring at the exact same
start_timeorend_time.
Hints
Hint 1
Because earnings arrive in chronological order, appending values to sorted lists allows you to use binary search for range queries.
Hint 2
Pairing timestamps with cumulative prefix sums allows you to compute range totals in O(log N) time rather than O(N).
Hint 3
Maintain both per-driver time series and a global time series to answer driver-specific and company-wide queries with the same prefix sum technique.
Follow-up questions
- How would you handle out-of-order earnings (e.g., late tips or delayed network syncs)?
- How would you efficiently implement a method `get_top_k_drivers(start_time: int, end_time: int, k: int) -> list[str]`?
- If memory becomes a constraint, how would you evict or archive older data while still answering historical aggregate queries accurately?
Solution walkthrough is for members
Get the full walkthrough with reference code and complexity analysis, plus Kitty Coach at 300 messages a day. Hints, the code runner and community answers stay free.