python >= operator on classes -


i have question regarding python '>=' behaviour.

i have old timestamp class, holds (hour, minute) tuple , offers methods such __eq__, __gt__, __lt__.

i refactoring account day , second, , store data total seconds. here implemented __eq__, __gt__, __lt__ well.

however, further in code using >= operator class , while old class version working properly, new 1 getting

typeerror: unorderable types: timestamp() >= timestamp() error. 

code below:

class timestamp(tuple): # old, working version     """timestamp, hh:mm tuple supporting comparison , addition"""     __slots__ = ()     def __new__(cls, *args):         if len(args) == 1:  # tuple entrance             hour, minute = args[0]         elif len(args) == 2: # hour, minute entrance             hour, minute = args[0], args[1]         else:             raise typeerror('wrong input timestamp')         div, minute = divmod(minute, 60)         hour += div         _, hour = divmod(hour, 24)         return tuple.__new__(cls, (hour, minute))      @property     def abs_min(self):         return self.hour * 60 + self.minute      def __gt__(self, rhs):         return self.abs_min > rhs.abs_min      def __lt__(self, rhs):         return self.abs_min < rhs.abs_min      def __eq__(self, rhs):         return self.abs_min == rhs.abs_min 

new version:

class timestamp:     def __init__(self, *args):         argument in args:             if not isinstance(argument, int):                 raise typeerror("can build timestamp ints, not: " + str(argument))          if len(args) == 1:  # init abs             self.abs = args[0] # put element, not tuple         elif len(args) == 2:    # init hour:minute             hour, minute = args             self.abs = hour * 60 * 60 + minute * 60         elif len(args) == 4:    #init day:hour:minute:second             day, hour, minute, second = args             self.abs = day * 24 * 60 * 60 + hour * 60 * 60 + minute * 60 + second         else:             raise typeerror("wrong data timestamp: " + str(args))      def __eq__(self, other):         if isinstance(other, timestamp):             return self.abs == other.abs         else:             raise typeerror("wrong argument comparison: " + str(other))      def __gt__(self, other):         if isinstance(other, timestamp):             return self.abs > other.abs         else:             raise typeerror("wrong argument comparison: " + str(other))      def __lt__(self, other):         if isinstance(other, timestamp):             return self.abs < other.abs         else:             raise typeerror("wrong argument comparison: " + str(other)) 

now comparison part:

if args[1] >= self.start: >>typeerror: unorderable types: timestamp() >= timestamp() 

i have found 2 fixes: first, replace comparison line with

if args[1] > self.start or args[1] == self.start: 

or alternative, add

def __ge__(self, other):     if isinstance(other, timestamp):         return self.abs >= other.abs     else:         raise typeerror("wrong argument comparison: " + str(other)) 

to new class. however, old 1 did work neither of fixes. looks me if python stopped deducting ((a>b) or (a==b)) implies (a>=b). why did work before? have me subclassing tuple?

ps. don't scared __init__ code, included completeness. it's supposed overload-like, might doing in non-pythonic way (still learning)

the old 1 worked because inherited tuple, , tuple provides __ge__. new version not inherit tuple, doesn't have __ge__ method.

even in old version, __gt__ , __lt__ methods never being called when using >= (as can verify putting print inside methods). underlying tuple.__ge__ being called instead. however, case, effect same, didn't notice. is, given "minutes" number less 60, comparing (hours, minutes) tuples in usual way equivalent comparing 60*hours + minutes. don't think need define comparison methods @ if inherit tuple.


Comments

Popular posts from this blog

java - Custom OutputStreamAppender not run: LOGBACK: No context given for <MYAPPENDER> -

java - UML - How would you draw a try catch in a sequence diagram? -

c++ - No viable overloaded operator for references a map -