8. class Philosopher(JSONStore):
'''JSONStore provides `load` and `save`'''
store = './lyceum'
dump_these = ('name', ‘rep’, 'works’)
def __init__(self, name, rep=5, works=tuple()):
self.name = name
self.rep = rep
self.works = list(works)
super(Philosopher,
self).__init__(name.lower())
def __eq__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, ‘id’):
return self.id == other.id
return NotImplemented
9. class Philosopher(JSONStore):
'''JSONStore provides `load` and `save`'''
store = './lyceum'
dump_these = ('name', ‘rep’, 'works’)
def __init__(self, name, rep=5, works=tuple()):
self.name = name
self.rep = rep
self.works = list(works)
super(Philosopher,
self).__init__(name.lower())
def __eq__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, ‘id’):
return self.id == other.id
return NotImplemented
10.
11. There are no implied relationships among the
comparison operators. The truth of x == y does
not imply that x != y is false. Accordingly, when
defining __eq__(), one should also define
__ne__() so that the operators will behave as
expected.
5 Minutes Later …
12. class Philosopher(JSONStore):
# ... snip
def __eq__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, ‘id’):
return self.id == other.id
return NotImplemented
def __ne__(self, other):
is_eq = self.__eq__(other)
if is_eq is NotImplemented:
return is_eq
return not is_eq
13. class Philosopher(JSONStore):
# ... snip
def __eq__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, ‘id’):
return self.id == other.id
return NotImplemented
def __ne__(self, other):
is_eq = self.__eq__(other)
if is_eq is NotImplemented:
return is_eq
return not is_eq
20. 5 Seconds Later …
There are no swapped-argument versions of
these methods (to be used when the left
argument does not support the operation but
the right argument does); rather, __lt__() and
__gt__() are each other’s reflection, __le__()
and __ge__() are each other’s reflection, and
__eq__() and __ne__() are their own reflection.
21. class Philosopher(JSONStore):
# ... Snip
def __gt__(self, other):
print ’{}: called __gt__’.format(self.name)
if isinstance(self, other.__class__)
and hasattr(other, 'rep'):
return self.rep > other.rep
return NotImplemented
22. >>> aristotle > kant
Aristotle: called __gt__
True
>>> kant < aristotle
Aristotle: called __gt__
True
23. NotImplemented
This type has a single value. There is a single
object with this value … Rich comparison
methods may return this value if they do not
implement the operation for the operands
provided. (The interpreter will then try the
reflected operation, or some other fallback,
depending on the operator.)
35. @functools.total_ordering
class Philosopher(JSONStore):
# ... snip
def __eq__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, ‘id’):
return self.id == other.id
return NotImplemented
def __gt__(self, other):
if isinstance(self, other.__class__)
and hasattr(other, 'rep'):
return self.rep > other.rep
return NotImplemented
def __ne__(self, other):
# snip ...
36.
37. class X(object):
def __eq__(self, other):
return lambda x: x == other
def __ne__(self, other):
return lambda x: x != other
def __lt__(self, other):
return lambda x: x < other
def __le__(self, other):
return lambda x: x <= other
def __gt__(self, other):
return lambda x: x > other
def __ge__(self, other):
return lambda x: x >= other
x = X()