Python 3中的可比较类

Nei*_*l G 9 python class comparable python-3.x

在Python 3中使类可比的标准方法是什么?(例如,通过id.)

Len*_*bro 9

对于一整套比较函数,我使用了下面的mixin,你可以在模块中输入一个mixin.py.

class ComparableMixin(object):
    def _compare(self, other, method):
        try:
            return method(self._cmpkey(), other._cmpkey())
        except (AttributeError, TypeError):
            # _cmpkey not implemented, or return different type,
            # so I can't compare with "other".
            return NotImplemented

    def __lt__(self, other):
        return self._compare(other, lambda s, o: s < o)

    def __le__(self, other):
        return self._compare(other, lambda s, o: s <= o)

    def __eq__(self, other):
        return self._compare(other, lambda s, o: s == o)

    def __ge__(self, other):
        return self._compare(other, lambda s, o: s >= o)

    def __gt__(self, other):
        return self._compare(other, lambda s, o: s > o)

    def __ne__(self, other):
        return self._compare(other, lambda s, o: s != o)
Run Code Online (Sandbox Code Playgroud)

要使用上面的mixin,您需要实现一个_cmpkey()方法,该方法返回可以比较的对象的键,类似于排序时使用的key()函数.实现可能如下所示:

>>> from .mixin import ComparableMixin

>>> class Orderable(ComparableMixin):
...
...     def __init__(self, firstname, lastname):
...         self.first = firstname
...         self.last = lastname
...
...     def _cmpkey(self):
...         return (self.last, self.first)
...
...     def __repr__(self):
...         return "%s %s" % (self.first, self.last)
...
>>> sorted([Orderable('Donald', 'Duck'), 
...         Orderable('Paul', 'Anka')])
[Paul Anka, Donald Duck]
Run Code Online (Sandbox Code Playgroud)

我使用它而不是total_ordering配方的原因是这个错误.它已在Python 3.4中修复,但通常您也需要支持较旧的Python版本.


agf*_*agf 8

sort只需要__lt__.

functools.total_ordering (截至2.7/3.2)是一个提供所有比较运算符的装饰器,因此您不必自己编写所有这些运算符.

默认情况下,类是可清除的,这使用它们id(); id()除非你只是希望订单稳定,否则我不确定你为什么要订购他们的课程.

  • 这已在 3.4 中修复,这可能是最好的答案。 (3认同)
  • +1只是想提及搜索这个装饰的其他人可以作为`functools.total_ordering`. (2认同)