Reputation: 1
I am developing an application where users can make a reservation for a car and the fee for the reservation depends on which hours and which day of the week the reservation takes places.
The rules for the fee calculation are:
Example reservation:
start: Monday, 2023/02/06 - 07:00 am end: Monday, 2023/02/20 - 07:00 am
Calculation:
10 weekdays (monday-friday during the day) with 12 hours * 2.00 = 240.00
10 weekdays (monday-friday during the night) with 12 hours * 0.50 = 60.00
4 weekend days with 24 hours per day * 0.50 CHF = 48.00
This results in a total fee of 348.00
I am wondering how I could solve this with a function in python with calculates the start date and end dates with dependies on the 3 rules from above.
I even don't know how to start in order to extract the hours and days from the start date and end date.
Upvotes: 0
Views: 101
Reputation: 1921
To calculate the fee for a given reservation, you can write a Python function that takes the start and end dates of the reservation as inputs, and uses datetime module to extract the hours and days from the dates.
import datetime
def calculate_reservation_fee(start_date, end_date):
weekdays_day_rate = 2.00 # rate for weekdays during the day
weekdays_night_rate = 0.50 # rate for weekdays during the night
weekend_rate = 0.50 # rate for weekends
total_fee = 0.00
# iterate over all hours in the reservation period
current_date = start_date
while current_date < end_date:
hour = current_date.hour
day_of_week = current_date.weekday() # 0 is Monday, 6 is Sunday
if day_of_week < 5 and 7 <= hour < 19: # weekday during the day
total_fee += weekdays_day_rate
elif day_of_week < 5: # weekday during the night
total_fee += weekdays_night_rate
else: # weekend
total_fee += weekend_rate
# move to the next hour
current_date += datetime.timedelta(hours=1)
return total_fee
Upvotes: 1
Reputation: 121
This snippet takes input strings as in your example and when executed prints 348 as the desired price. It uses a list to store all prices so it isn't too hard to modify in future if prices change. When index
gets to the end of the weekly prices list index
will be set back to zero so you can keep adding up the hours as the weeks roll over.
import datetime
# assuming your input format is strings like this
input_start = "Monday, 2023/02/06 - 07:00 am"
input_end = "Monday, 2023/02/20 - 07:00 am"
# cut out the weekday as it doesn't matter
start = datetime.datetime.strptime(input_start.split(", ")[1], "%Y/%m/%d - %I:%M %p")
end = datetime.datetime.strptime(input_end.split(", ")[1], "%Y/%m/%d - %I:%M %p")
# now make a list hourly_prices_week of all the prices of each hour in the week
# the list should be 168 in length (168 hours in a week)
# to build it faster fill in the weekday and weekend first
hourly_prices_weekday = [0.5] * 7 + [2] * 12 + [0.5] * 5
hourly_prices_weekend = [0.5] * 24
# add the 5 weekdays and then 2 weekend days
# note the prices start at the begining of monday
hourly_prices_week = hourly_prices_weekday * 5 + hourly_prices_weekend * 2
print(hourly_prices_week) # [ 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 2, 2, 2, ....]
print(len(hourly_prices_week)) # 168
# find out how many hours are between start and end times
hours = (end - start).total_seconds() / 3600
print(hours) # 336
# determine what index of hourly_prices your start time is in
index = 0 # this is start of monday
index += start.weekday() * 24 # go forward however many days (monday is 0)
index += start.hour # go forward however many hours (hour is 0-23)
print(index) # 7
price = 0
while hours > 0:
price += hourly_prices_week[index]
index += 1
if index >= len(hourly_prices_week):
index = 0
hours -= 1
print(price) # 348
Upvotes: 0
Reputation: 3285
I made an example with a custom class built on top of the datetime module, that overrides the subtract method __sub__
.
The cost
method defines what the price should be in each hour interval using your rules above.
The function date_range
from pandas is used to generate each hour between the two dates, which I then apply the cost
function on to get the total price
import datetime as dt
from pandas import date_range
class Rental(dt.datetime):
def __sub__(self, other):
times = date_range(self, other, freq='H', inclusive='left')
return sum(self.cost(d) for d in times)
@staticmethod
def cost(time):
if time.weekday() > 4:
return 0.5
if 7 <= time.hour < 19:
return 2
return 0.5
print(Rental(year=2022, month=3, day=20, hour=0) - Rental(year=2022, month=4, day=3, hour=0))
>>> 348.0
Upvotes: 0