見出し画像

Python -特殊メソッド-

Pythonには、クラスを強力かつ柔軟にするための「特殊メソッド」(マジックメソッドとも呼ばれます)が多数存在する。これらの特殊メソッドを使うことで、クラスに特定の振る舞いを持たせたり、組み込みの操作をカスタマイズしたりできる


1. 特殊メソッド (Magic Methods)

特殊メソッドは、ダンダーメソッドとも呼ばれ、名前の前後にダブルアンダースコアがついているメソッド。これらのメソッドは、Pythonの特定の動作をカスタマイズするために使用される

代表的な特殊メソッド

__init__: コンストラクタメソッド。オブジェクトが生成される際に呼び出され、インスタンス変数の初期化を行う

class MyClass:
    def __init__(self, value):
        self.value = value

__str__: オブジェクトの文字列表現を返すメソッド。print()やstr()関数で呼び出される

class MyClass:
    def __init__(self, value):
        self.value = value

    def __str__(self):
        return f"MyClass with value: {self.value}"

obj = MyClass(10)

print(obj)  
# 出力: MyClass with value: 10

__repr__: オブジェクトの「公式」な文字列表現を返すメソッド。repr()関数やインタプリタでの表示に使われる

class MyClass:
    def __repr__(self):
        return f"MyClass({self.value})"

__len__: len()関数に対応し、オブジェクトの長さを返す

class MyList:
    def __init__(self, items):
        self.items = items

    def __len__(self):
        return len(self.items)

my_list = MyList([1, 2, 3])

print(len(my_list))  
# 出力: 3

__getitem__: インデックスアクセスを可能にするメソッド。obj[key]で呼び出される

class MyList:
    def __init__(self, items):
        self.items = items

    def __getitem__(self, index):
        return self.items[index]

my_list = MyList([1, 2, 3])

print(my_list[0])  
# 出力: 1

__add__: +演算子をオーバーロードするためのメソッド

class MyNumber:
    def __init__(self, value):
        self.value = value

    def __add__(self, other):
        return MyNumber(self.value + other.value)

    def __str__(self):
        return str(self.value)

num1 = MyNumber(10)
num2 = MyNumber(20)
result = num1 + num2
print(result)  # 出力: 30

2. クラスの応用

クラスの応用では、特殊メソッドを活用してカスタムデータ構造を作成したり、オブジェクトの動作を制御したりできる

カスタムデータ構造の作成

class Stack:
    def __init__(self):
        self.items = []

    def push(self, item):
        self.items.append(item)

    def pop(self):
        return self.items.pop()

    def __len__(self):
        return len(self.items)

    def __str__(self):
        return str(self.items)

stack = Stack()
stack.push(1)
stack.push(2)
stack.push(3)

print(stack)  # 出力: [1, 2, 3]
stack.pop()
print(stack)  # 出力: [1, 2]
print(len(stack))  # 出力: 2

解説: Stack クラスは、スタックデータ構造を表現している。push メソッドで要素を追加し、pop メソッドで要素を取り出す。__len__や__str__メソッドを追加することで、スタックの長さや内容を簡単に確認できるようにしている

イミュータブルクラスの作成

イミュータブル(不変)オブジェクトとは、一度作成されると、その内容が変更されないオブジェクトのこと

class ImmutablePoint:
    def __init__(self, x, y):
        self._x = x
        self._y = y

    @property
    def x(self):
        return self._x

    @property
    def y(self):
        return self._y

    def __repr__(self):
        return f"ImmutablePoint({self._x}, {self._y})"

# 作成後は属性を変更できない
point = ImmutablePoint(10, 20)
print(point)  # 出力: ImmutablePoint(10, 20)

解説: ImmutablePoint クラスでは、@property デコレータを使って属性を読み取り専用にしている。これにより、オブジェクトの内容を変更することなく、安全に使用することができる

演算子オーバーロードを活用した複雑なオブジェクト操作

class Vector:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __add__(self, other):
        return Vector(self.x + other.x, self.y + other.y)

    def __sub__(self, other):
        return Vector(self.x - other.x, self.y - other.y)

    def __repr__(self):
        return f"Vector({self.x}, {self.y})"

v1 = Vector(2, 3)
v2 = Vector(4, 5)
print(v1 + v2)  # 出力: Vector(6, 8)
print(v1 - v2)  # 出力: Vector(-2, -2)

解説: Vector クラスでは、__add__ および __sub__ メソッドを使ってベクトルの加算と減算をサポートしている。これにより、ベクトル同士の演算が直感的に行えるようになる

いいなと思ったら応援しよう!