LoginSignup
9

More than 5 years have passed since last update.

Pythonのクラスで__eq__などを汎用的に実装する

Last updated at Posted at 2013-10-17

定義したクラスに関して比較演算子を適用したい場合は、拡張比較(rich comparison)メソッドを実装します。
例として人を表すクラスを考えてみると、以下のようになります。

class Person(object):
    def __init__(self, firstname, lastname, email):
        self.firstname = firstname
        self.lastname = lastname
        self.email= email
    def __eq__(self, other):
        if other is None or not isinstance(other, Person): return False
        # 以下がめんどい
        return self.firstname == other.firstname and
            self.lastname == other.lastname and
            self.email == other.email
    def __ne__(self, other):
        return not self.__eq__(other)

クラスを定義するたびに self.xxx == other.xxx and ... なんて書くのは正直めんどいわけです。
なので基底クラスから継承したdictメソッドを利用することにします。

class Person(object):
    def __init__(self, firstname, lastname, email):
        self.firstname = firstname
        self.lastname = lastname
        self.email= email
    def __eq__(self, other):
        # isinstance(other, Person)を除去
        if other is None or type(self) != type(other): return False
        # __dict__メソッドを使ってattributesを比較
        return self.__dict__ == other.__dict__
    def __ne__(self, other):
        return not self.__eq__(other)

これでアトリビュート名を書くことなく、汎用的な形で2つのオブジェクトを比較できます。
assertEqualsも余裕で通ります。
アトリビュートがeqメソッドを持っていることが前提ですけどね。

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9