0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Python の特殊メソッド(ダンダーメソッド)紹介。 オブジェクト同士の加算や、オブジェクトの表示をカスタマイズ

Last updated at Posted at 2024-07-27

はじめに

Pythonにはたくさんの特殊メソッド(ダンダーメソッド)がありますが、今回は自作クラスに使えるものを紹介します。

本文

今回の前提

説明するのに使う体重classです。
このクラスには、体重だけでなく、測定した日付も格納されています。
それぞれ、A君、B君のインスタンスを生成しています。

class Body_weight:
    def __init__(self,weight,recorded_date) -> None:
        # 体重
        self.weight = weight
        # 体重の測定した日付
        self.recorded_date = recorded_date

A_weight = Body_weight(75,"2024-1-20")
B_weight = Body_weight(46,"2023-11-21")

紹介するメソッドの一覧

メソッド名 呼び出せれるタイミング
__str__ print(obj)
__int__ int(obj)
__add__ obj + hoge

__str__ の説明

printされた時に呼び出されます。
これを定義しないと通常では下記のようになります。

A_weight = Body_weight(75,"2024-1-20")
print(A_weight)

""" 出力 """
# <__main__.Body_weight object at 0x0000025F70832310>

ですが、下記のように定義すると...

class Body_weight:
    def __init__(self,weight,recorded_date) -> None:
        # 体重
        self.weight = weight
        # 体重の測定し日付
        self.recorded_date = recorded_date
        
    def __str__(self):
        return f"測定日:{self.recorded_date}  体重:{str(self.weight)}"
        
A_weight = Body_weight(75,"2024-1-20")
print(A_weight)

"""出力"""
# 測定日:2024-1-20  体重:75

このように表示してくれるようになります。

__int__ の説明

intへキャストする時に呼び出されます。
これを定義しないと通常では下記のようになります。

A_weight = Body_weight(75,"2024-1-20")
print(int(A_weight))

"""出力"""
# TypeError: int() argument must be a string, a bytes-like object or a real number, not 'Body_weight'

Errorになっちゃいますね。
ですが、下記のように定義すると...

class Body_weight:
    def __init__(self,weight,recorded_date) -> None:
        # 体重
        self.weight = weight
        # 体重の測定し日付
        self.recorded_date = recorded_date
        
    def __int__(self):
        return self.weight

A_weight = Body_weight(75,"2024-1-20")
print(int(A_weight))

"""出力"""
# 75

しっかりとキャストしくれるようになります。

__add__ の説明

加算の処理の時に呼び出されるものです。
これを定義しないと通常では下記のようになります。

A_weight = Body_weight(75,"2024-1-20")
print(A_weight + 100)

"""出力"""
# TypeError: unsupported operand type(s) for +: 'Body_weight' and 'int'

Errorになっちゃいますね。
ですが、下記のように定義すると...

class Body_weight:
    def __init__(self,weight,recorded_date) -> None:
        # 体重
        self.weight = weight
        # 体重の測定し日付
        self.recorded_date = recorded_date
    
    def __add__(self, other):
        return self.weight  + other

A_weight = Body_weight(75,"2024-1-20")
print(A_weight + 100)

"""出力"""
# 175

しっかし加算してくれましたが、まだ、下記の場合に対応できていません!

A_weight = Body_weight(75,"2024-1-20")
B_weight = Body_weight(46,"2023-11-21")

print(A_weight + B_weight)

"""出力"""
# unsupported operand type(s) for +: 'int' and 'Body_weight'

このエラーがでる原因は、__add__の引数のotherがintでないからですね...
先ほど紹介した__int__を組み合わせると解決します!

class Body_weight:
    def __init__(self,weight,recorded_date) -> None:
        # 体重
        self.weight = weight
        # 体重の測定し日付
        self.recorded_date = recorded_date

    def __int__(self):
        return self.weight
    
    def __add__(self, other):
        return self.weight  + int(other)

A_weight = Body_weight(75,"2024-1-20")
B_weight = Body_weight(45,"2023-11-21")

print(A_weight + B_weight)

"""出力"""
# 120

これで、加算対象がint型でも同じBody_weightでも動くようになりました!

その他の演算

加算以外にも、以下のような演算をオーバーライド可能です。

メソッド名 呼び出せれるタイミング
__mul__ obj * 2
__truediv__ obj / 2
__mod__ obj % 2

最後に

覚えておくといつか使えそうですよね。
調べてみてとても楽しかった。

0
0
0

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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?