Create a Time
class.
Specification
Basic attributes: hour, minute, second and day (default is 0), + getters, + setters (using a decorator)
If you try to initialize an incorrect value of seconds or minutes, i.e. greater than or equal to 60, raise an exception from your own
WrongSeconds
orWrongMinutes
class
Add the following operators:
+
: works as follows - adds hours to hours, minutes to minutes, and so on, e.g. 2 h 30 m 4 s + 6 h 35 m 50 s = 9 h 5 m 54 s (we also return an instance of the Time class), if we exceed 24 h, the day should be 1<: Compare first day, hours, then minutes, seconds. Return True / False, e.g. 2 h 40 m 30 s d 0 < 1 h 59 m 30 s d 0 → False, 2 h 40 m 30 s d -1 < 1 h 59 m 30 s d 0 → True
__str__
:Time
should be displayed as: "20:05:25, day without any changes" (when day = 1, -1 : next / previous day)
Add the function zone
, which for a given instance of the Time
class returns the appropriate time in another time zone. The argument of the function is the city for which we find the time: Warsaw, London, New York, Tokyo, Syndey, Moscow, Los Angeles. We assume that the default time is GMT.
- PEP8
- DOC
- tests
And here is the code!
class WrongSeconds(Exception):
def __str__(self):
return "Wrong amount of seconds passed (greater or equal 60)"
class WrongMinutes(Exception):
def __str__(self):
return "Wrong amount of minutes passed (greater or equal 60)"
class Time:
TIME_ZONES = { "Warsaw": 2,
"London": 1,
"Tokio": 9,
"Sydney": 10,
"Moscow": 3,
"Los angeles": -7 }
def __init__(self, d = 0, h = 0, m = 0, s = 0):
self.days = d
self.hours = h
self.minutes = m
self.seconds = s
@property
def days(self):
return self._d
@days.setter
def days(self, val):
self._d = val
@property
def hours(self):
return self._h
@hours.setter
def hours(self, val):
if val < 0:
self.days += val//60
val = 24 - abs(val)%24
elif val >= 24:
self.days += val//24
val %= 24
self._h = val
@property
def minutes(self):
return self._m
@minutes.setter
def minutes(self, val):
if "_m" not in self.__dict__ and val >= 60:
raise WrongMinutes
if val < 0:
self.hours += val//60
val = 60 - abs(val)%60
elif val >= 60:
self.hours += val//60
val %= 60
self._m = val
@property
def seconds(self):
return self._s
@seconds.setter
def seconds(self, val):
if "_s" not in self.__dict__ and val >= 60:
raise WrongSeconds
if val < 0:
self.minutes += val//60
val = 60 - abs(val)%60
elif val >= 60:
self.minutes += val//60
val %= 60
self._s = val
def strefa(self, city):
if city.capitalize() not in self.TIME_ZONES: raise ValueError(f"City {city} not in time zone database")
result_time = self.__class__( self.days, self.hours, self.minutes, self.seconds)
result_time.hours += self.TIME_ZONES[city.capitalize()]
return str(result_time)
def __add__(self, other):
assert isinstance(other, self.__class__), f"Cannot add {type(other)} to a time object"
result = self.__class__()
result.seconds += self.seconds + other.seconds
result.minutes += self.minutes + other.minutes
result.hours += self.hours + other.hours
result.days += self.days + other.days
return result
def __lt__(self, other):
assert isinstance(other, self.__class__), f"Cannot compare {type(other)} with a time object"
if self.days < other.days: return True
elif self.hours < other.hours: return True
elif self.minutes < other.minutes: return True
elif self.seconds < other.seconds: return True
return False
def __str__(self):
s = f"{self.hours}:{self.minutes:02}:{self.seconds:02}"
if self.days == 0 :
return s + ", day without any changes"
elif self.days == 1 :
return s + ", the next day"
elif self.days == -1 :
return s + ", previous day"
return s + f", day: {self.days}"
# --- TEST CASES ---
try:
time = Time(m = 60)
except Exception as e:
print(e.__class__, e, "\n")
time = Time(d = 0, h = 23, m = 59, s = 59)
print(time)
time.seconds += 1
print(time, "\n")
time1 = Time(h = 3, m = 2, s = 1)
time2 = Time(h = 6, m = 5, s = 4)
print(time1 + time2, "\n")
print(time1 < time2 )
print(time2 < time1, "\n")
time_gmt = Time(h = 2, m = 0, s = 0)
print(time_gmt.strefa("London"))
print(time_gmt.strefa("Sydney"))
print(time_gmt.strefa("Los Angeles"))
print("------------------------------------")
print("Comparisons")
t1 = Time(h = 14, m = 4, s = 35)
t2 = Time(h = 8, m = 50, s = 25)
print(t1 + t2)
print(t1)
print(t2)
print(t1 < t2)
Output:
<class '__main__.WrongMinutes'> Wrong amount of minutes passed (greater or equal 60)
23:59:59, day without any changes
0:00:00, the next day
9:07:05, day without any changes
True
False
3:00:00, day without any changes
12:00:00, day without any changes
19:00:00, previous day
------------------------------------
Comparisons
22:55:00, day without any changes
14:04:35, day without any changes
8:50:25, day without any changes
True
And here is my question, how to get a better solution? Maybe shorter? Maybe get rid of some operations, terms?
<
,<=
,>
,>=
,==
and!=
. Otherwise, the whoever used yourTime
class might run into trouble during comparisons without noticing. \$\endgroup\$