Атрибуты класса foo = ИмяКласса() содержат поля и методы:
Поляя
public self.a (обращение: foo.a)
protected self._b (обращение: foo._b)
private self.__c (обращение: foo._ИмяКласса__c)
Методы
public self.func(self,...) (обращение: foo.func(...))
private self.__func(self,...)
магические self.__func__(self,...)
Конструктор __new__ (обычныо не используется)
Инициализатор __init__(self, аргументы...)
Деструктор __del__ (отработает, даже если __init__ упадёт)
Примеры:
# Пустой классclass ИмяКласса: pass# Пример №1class ИмяКласса: a = 1 def __init__(self, b, c): # Правило хорошего тона - все поля должны возникнуть внутри __init__-а. self.b = b self.c = cfoo1 = ИмяКласса(2,3)foo2 = ИмяКласса(4,5)ИмяКласса.a = 10 # Значение поля a поменялось у всех переменных класса ИмяКлассаprint(foo1.a, foo2.a)foo1.a = 20 # Значение поля a поменяется только у переменной foo1.aprint(foo1.a, foo2.a)
Наследование
Для наследования после имени класса указывается родительский класс: class B(A):
Передаются все атрибуты, даже __init__ с инициализируемыми в нём полями. Для того, чтобы атрибуты были новыми, они просто объявляются с теми же именами.
Private поля наследуются только в общедоступном виде self._РодительскийКласс__a
Примеры:
class A: def __init__(self, a=1): self.a = aclass B(A): passclass C(A): def __init__(self): super().__init__(2) # Дальше инит продолжается стандартно ...print(B().a) # 1print(C().a) # 2
Перегрузка методов
Беcклассовая перегрузка методов − разное исполнение методов класса при разных передаваемых аргументах (тип, длина и т.д.). Например, функция разности может возвращать число при численных аргументах, строку при аргументах-строках.
Перегрузка методов в классе в основном используется для магических методов.
Логические внутренние методы класса:
__eq__→a == b
__ne__→a != b
__lt__→a < b
__le__→a <= b
__gt__→a > b
__ge__→a >= b
Арифметические внутренние методы класса:
__add__→a + b
__mul__→a * b
__sub__→a - b
__mod__→a % b
__truedib__→a / b
Другие методы:
__repr__(self)− как виден экземпляр класса в отладчике и консоли
__str__(self)− как объект превратится в строку (например, в print)
__call__(self, args)− вызов экземпляра класса как функции
__hash__(self)− вычисляет хеш для экземпляра класса hash(...)
Он нужен, чтобы понимать различие между переменными этого класса. Например, когда переменные класса образуют set или ключи dict.
class A: def __init__(self, a=1, b=2, c=3): self.a = a self.b = b self.c = c def __str__(self): return f"Класс А с полями a={self.a} и b={self.b}" def __eq__(self, other): return self.a == other.a and self.b = other.b def __hash__(self): # Здесь хэш считается по tuple, в который включены два поля. # Хэши для двух экземпляров класса будут разные, если значение хотя бы одно из полей у них разное. # Логически это как будто очень близко к __eq__, но технически используется для совсем других целей. return hash((self.data, self.tag))foo1 = A(1,2,3)foo2 = A(1,2,4)print(foo1)print(foo1 == foo2)