特殊属性¶
クラスには特殊属性と呼ばれるメソッドが存在しており、クラスを使う際に使用される構文はどれも特殊属性の呼び出しに変換されて実行されます。代表的な特殊属性をいくつか紹介します。
下記のようなクラスを定義したときの特殊属性には次のようなものがあります。
import math
class Point:
"""Point クラスです。"""
def __init__(self, x, y):
self.x = x
self.y = y
def distance(self):
return math.sqrt(self.x * self.x + self.y * self.y)
__doc__¶
Point.__doc__ という変数には """Point クラスです。""" という文字列が入ります。""" ... """ というトリプルクオテーションでくくられた文字列は改行を含む複数行の文字列を定義できる文字列です。
"""この文字列は
一つの文字列として
扱われます。"""
__doc__ は docstring と呼ばれ、ドキュメンテーションをする際に使用される文字列として扱われます。
__init__¶
クラスインスタンスを作成するときは __init__() が呼び出されます。
point = Point(10, 20) # point.__init__(10, 20)
__getattribute__¶
クラスのメンバやメソッドを参照したときは __getattribute__() が呼び出されます。
point = Point(10, 20)
point.x # point.__getattribute__('x')
point.distance() # point.__getattribute__('distance')()
__getattr__¶
__getattribute__() でのメンバ参照に失敗した場合は __getattr__() が呼び出されます。このような事が起こるのはクラスのメンバとして定義されていないものにアクセスしようとしたときに起こります。
point.x2 # point.__getattr__('x2')
__getattr__() は明示的には定義されません。使用するには自分で定義する必要があります。
class Point:
...
def __getattr__(self, item):
if item == 'x2':
return self.x * self.x
elif item == 'y2':
return self.y * self.y
__getitem__¶
クラスインスタンスに対して [] を使用した際には __getitem__() が呼び出されます。
point = Point(10, 20)
point['x'] # point.__getitem__('x')
__getitem__() を使用するには自分で定義する必要があります。
class Point:
...
def __getitem__(self, item):
if item == 'x':
return self.x
elif item == 'y':
return self.y
__setattr__¶
メンバへの代入が行われた場合は __setattr__() が呼び出されます。
point = Point(10, 20)
point.x = 30 # point.__setattr__('x', 30)
__eq__¶
インスタンスに対して == が使用された場合は __eq__() が呼ばれます。
point1 = Point(10, 20)
point2 = Point(30, 40)
point1 == point2 # point1.__eq__(point2)
その他類似の特殊属性が下記の通り用意されています。
| 特殊属性 | 意味 |
|---|---|
__ne__ |
point1 != point2 |
__le__ |
point1 <= point2 |
__lt__ |
point1 < point2 |
__ge__ |
point1 >= point2 |
__gt__ |
point1 > point2 |
__str__¶
クラスインスタンスに対して文字列型へのキャストを行うと __str__() が呼び出されます。明示的なキャストでなくても文字列への変換が必要とされるケースでも同様の振る舞いをします。
point = Point(10, 20)
print(point) # print(point.__str__())
__str__() はデフォルトで定義されていますが、大抵の場合は有益な文字列にはなっていないので自分で定義したほうが良いです。
class Point:
...
def __str__(self):
return f'<Point(x={self.x}, y={self.y})>'