Blow Up by Black Swan

Python-特殊メソッド: __repr__と__str__

今回は、Pythonの特殊メソッドの中でも特にややこしい__repr____str__について挙動を確認しながらその特徴を検証しようと思います。色々調べる中で意外にこの2つの説明やコードについてわかりやすいものがなかったので、自分で記事を書くことにしました。なお、コードの検証にはjupyter labを使用しています。

1. Pythonの特殊メソッド、__repr__と__str__

Pythonにはクラスを作るときに活用できる特殊メソッドというものがあります。特殊メソッドはメソッドのオーバーライドを行うときに利用されるもので、オブジェクト指向の大きな特徴であるポリモーフィズムを簡単に実装できるようにしている仕組みとも言えるかもしれません。その中で今回は__repr____str__です。これはどちらも文字列で出力結果を返す特殊メソッドですが、それぞれ下記のような特徴があります。

  • __repr__()
    • オフィシャルな出力結果
    • 戻り値は有効な式で定義するか、でなければ<>の中に有用な記述を行い、返すようにするのが良いとされている
    • jupyter notebookなどではprintを使わず、変数名を指定するだけで出力結果を得ようとするときに呼び出される
    • __str__が定義されていない場合にも代わりに呼び出される
    • 内部的には組み込み関数のrepr()が呼び出されている
  • __str__()
    • __repr__に対し非公式の出力結果という位置付け
    • 組み込み関数のprintやformat、strを使うときに呼び出されている
    • 表示用の特殊メソッドともいえ、__repr__が存在しない場合でもその代わりにはならない

2. __repr__と__str__をコードで検証

ここからはコードで挙動を検証していきます。まずは基本的な挙動と特徴からです。

# 基本
class Test:
    def __init__(self, args):
        self.value = args
    def __repr__(self):
        return "<repr> "+self.value
    def __str__(self):
        return "<str>"+self.value
test=Test("try")
#2つの出力結果
print(test)
test

戻り値

<str>try
[19]: <repr> try

変数名だけで指定した場合とprint文を使った場合とで呼び出されている特殊メソッドが異なることがはっきりとわかります。これが__repr____str__の大きな違いです。次は、__repr____str__のどちらかがかけている場合の挙動をみていきます。

# __repr__有り
# __str__無し
class Test:
    def __init__(self, args):
        self.value = args
    def __repr__(self):
        return "<repr> "+self.value
    #def __str__(self):
    #    return "<str>"+self.value
test=Test("try")
#2つの出力結果
print(test)
test


戻り値

<repr> try
[24]: <repr> try

__str__がない場合に__repr__が代わりを果たしています。一方でその逆は成り立ちません。

# __repr__無し
# __str__有り
class Test:
    def __init__(self, args):
        self.value = args
    #def __repr__(self):
    #    return "<repr> "+self.value
    def __str__(self):
        return "<str>"+self.value
test=Test("try")
#2つの出力結果
print(test)
test

戻り値

<str>try
[25]: <__main__.Test at 0x106b0d4a8>

上記のコードを見て頂くと__repr____str__の違いがわかると思います。

3. 参考サイトとまとめ

以上が今回の記事内容です。実際にモジュールを作るときなどにポイントになってくると思いますが、基本は上記のようになります。どなたかの参考になれば幸いです。今回の参考サイトは以下になります。