Вопрос с собеседования · Python

Что такое магические методы? Чем __str__ отличается от __repr__?

JuniorООП
Ещё спрашивают так:
  • Какие dunder-методы вы знаете?
  • Для чего нужен __repr__?
  • Как сделать объект сравнимым или поддерживающим len()?
Коротко

Магические методы (__имя__) — крючки, через которые объект поддерживает встроенные операции языка.

  • __repr__ — однозначное представление для разработчика, __str__ — читаемое для человека
  • print и str() берут __str__, а если его нет — __repr__

А ещё Ещё примеры: __eq__/__hash__, __len__, __iter__, __enter__/__exit__, __call__

Подробно

Python вызывает магические методы сам, когда вы используете встроенный синтаксис: len(x) → x.__len__(), a + b → a.__add__(b), a == b → a.__eq__(b), for → __iter__, with → __enter__/__exit__, obj() → __call__. Реализовав их, свой класс начинает вести себя как встроенный тип.

**__repr__ и __str__.**

  • __repr__ — для отладки и логов: однозначно описывает объект, в идеале так, чтобы по строке можно было его воссоздать: Point(x=1, y=2). Его показывают консоль, отладчик и контейнеры: print([p]) выведет repr элементов.
  • __str__ — для пользователя: print(p), str(p), f-строки.
  • Если __str__ нет, используется __repr__; наоборот — нет. Поэтому писать стоит хотя бы __repr__.

Сравнение и хеш. Переопределив __eq__, нужно позаботиться о __hash__: иначе объект станет нехешируемым. Для упорядочивания хватит __eq__ и __lt__ с декоратором functools.total_ordering.

@dataclass генерирует __init__, __repr__ и __eq__ сам.

Пример

class Point:
    def __init__(self, x, y):
        self.x, self.y = x, y
    def __repr__(self):
        return f"Point(x={self.x}, y={self.y})"
    def __str__(self):
        return f"({self.x}, {self.y})"
    def __eq__(self, other):
        return isinstance(other, Point) and (self.x, self.y) == (other.x, other.y)
    def __hash__(self):
        return hash((self.x, self.y))

p = Point(1, 2)
print(p)       # (1, 2)
print([p])     # [Point(x=1, y=2)] — у элементов repr

Что хотят услышать

  • Что такое магические методы и что их вызывает сам язык.
  • Различие назначения __repr__ и __str__, правило подстановки.
  • Несколько примеров за пределами строкового представления.
  • Связь __eq__ и __hash__.

Частые ошибки

  • Сказать, что __str__ и __repr__ взаимозаменяемы в обе стороны.
  • Переопределить __eq__ и забыть про __hash__.

Проверьте себя

Один верный вариант. Подумайте, потом откройте ответ.

Показать варианты и ответ
  • ✓__repr__ — однозначно для разработчика, __str__ — читаемо для человека; без __str__ берётся __repr__
  • ✗print всегда использует __repr__, даже если определён __str__, а без __repr__ Python подставит __str__
  • ✗__str__ и __repr__ всегда должны возвращать одно и то же
  • ✗Магические методы можно вызывать только напрямую, встроенные операции их не используют

Что спросят дальше

Разбор темы

Связанные вопросы

Партнёр платформы

Разбор собеседования с sotto

После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.

Разбор собеседования