Def str python что это
Магические методы: __str__, __repr__, __len__, __abs__
На этом занятии я расскажу о, так называемых, магических методах, которые предопределены в каждом классе и записываются через два подчеркивания вначале и в конце имен, например, так:
dunder-методами (от англ. сокращения double underscope)
Магические методы __str__ и __repr__
Чтобы лучше понять, как работают эти методы, объявим класс для описания кошек:
Если теперь перейти в консоль Python, импортировать этот класс из нашего текущего модуля ex1:
и создать его экземпляр:
то при выводе cat, увидим служебную информацию:
Если мы хотим ее как-то переопределить и отображать информацию в другом виде, формате, то как раз и используются магические методы __str__ и __repr__. Давайте для начала переопределим метод __repr__ и посмотрим как это отразится на выводе служебной информации о классе:
Обратите внимание, этот метод должен возвращать строку, поэтому здесь записан оператор return и формируемая строка. Что именно возвращать, мы решаем сами, в данном случае – это название класса и имя кошки.
Перезапустим консоль и снова импортируем измененный класс Cat. И, смотрите, теперь при создании экземпляра мы видим другую информацию при его выводе:
Как раз то, что определили в магическом методе __repr__. То же самое увидим и при использовании функции print и str. По идее, здесь должен отрабатывать другой магический метод __str__, но так как он у нас еще не переопределен, то автоматически выполняется метод __repr__.
Давайте добавим второй магический метод __str__ и посмотрим, как это повлияет на отображение данных:
Выполним повторное импортирование класса Cat, создадим его экземпляр и при отображении по ссылке:
по-прежнему будем видеть служебную информацию от метода __repr__. Однако, если выполнить отображение экземпляра класса через print или str, то будет срабатывать уже второй метод __str__. Вот в этом отличие этих двух магических методов.
Магические методы __len__ и __abs__
Их использование достаточно простое и очевидное. Давайте для примера представим, что у нас есть класс Point, который может хранить произвольный вектор координат точки и определим его так:
А, далее, по программе нам бы хотелось определять размерность координат с помощью функции len(), следующим образом:
Если сейчас запустить программу, то увидим ошибку, так как функция len не применима к экземплярам классов по умолчанию. Как вы уже догадались, чтобы изменить это поведение, можно переопределить магический метод __len__() и в нашем случае это можно сделать так:
Смотрите, мы здесь возвращаем размер списка __coords и если после этого запустить программу, то как раз это значение и будет выведено в консоль. То есть, магический метод __len__ указал, что нужно возвращать, в момент применения функции len() к экземпляру класса. Как видите, все просто и очевидно.
Следующий магический метод __abs__ работает аналогичным образом, только активируется в момент вызова функции abs для экземпляра класса, например, так:
Опять же, если сейчас выполнить программу, то увидим ошибку, т.к. функция abs не может быть напрямую применена к экземпляру. Но, если переопределить магический метод:
который возвращает список из абсолютных значений координат точки, то программа отработает в штатном режиме и мы увидим ожидаемый результат.
Вот так можно использовать эти два магических метода. Я, надеюсь, из этого занятия вы узнали, как применять четыре магических метода:
__str__, __repr__, __len__, __abs__
Видео по теме
#1: парадигма ООП, классы, экземпляры классов, атрибуты
#2: методы класса, параметр self, конструктор и деструктор
#4: объекты свойства (property) и дескрипторы классов
#5: статические свойства и методы классов, декоратор @staticmethod, создание синглетона
#6: простое наследование классов, режим доступа protected
#7: переопределение и перегрузка методов, абстрактные методы
#8: множественное наследование, функция super
#9: перегрузка операторов
#10: собственные исключения и итерабельные объекты
#11: функторы и менеджеры контекста
#12: нейронная сеть (пример реализации)
#14: полиморфизм в ООП на Python
#15: Моносостояние экземпляров класса
#16: Магические методы __str__, __repr__, __len__, __abs__
#17: Коллекция __slots__ для классов
#18: Как работает __slots__ с property и при наследовании классов
#19. Введение в обработку исключений
#20. Распространение исключений (propagation exceptions)
#21. Инструкция raise и пользовательские исключения
© 2021 Частичное или полное копирование информации с данного сайта для распространения на других ресурсах, в том числе и бумажных, строго запрещено. Все тексты и изображения являются собственностью сайта
Строковые представления экземпляров класса: методы __str__ и __repr__
Введение
Примеры
мотивация
Итак, вы только что создали свой первый класс в Python, аккуратный маленький класс, который инкапсулирует игральную карту:
В другом месте вашего кода вы создаете несколько экземпляров этого класса:
Вы даже создали список карт, чтобы представить «руку»:
Теперь, во время отладки, вы хотите посмотреть, как выглядит ваша рука, поэтому вы делаете то, что естественно, и пишете:
В замешательстве вы пытаетесь просто напечатать одну карту:
И снова, вы получите этот странный вывод:
Не бойся Мы собираемся это исправить.
Что на самом деле произошло, так это то, что вы попросили Python «выразить словами» суть этого объекта и затем показать его вам. Более явная версия того же механизма может быть:
В первой строке, вы пытаетесь превратить Card экземпляр в строку, а во втором вы его отображения.
Эта проблема
Решение (часть 1)
Рассмотрим следующий, обновленную версию нашего Card класса:
Возвращаясь к нашей проблеме отображения карты в более удобной для пользователя форме, если мы снова запустим:
Мы увидим, что наш вывод намного лучше:
Так здорово, мы закончили, верно?
Итак, мы перепроверили следующий код:
И, к нашему удивлению, мы снова получаем эти забавные шестнадцатеричные коды:
Решение (часть 2)
Ну, механизм закулисности немного отличается, когда Python хочет получить строковое представление элементов в списке. Оказывается, Python не заботится о __str__ для этой цели.
Теперь мы можем видеть, какой метод отвечает за каждый случай:
И кроме того, если определено, мы могли бы назвать методы напрямую (хотя это кажется немного неясным и ненужным):
Так, чтобы было ясно, рассмотрим следующую версию Card класса:
как это делают вызовы repr() :
Резюме
Реализованы оба метода, стиль eval-round-trip __repr __ ()
Синтаксис
Параметры
Примечания
Научим основам Python и Data Science на практике
Это не обычный теоритический курс, а онлайн-тренажер, с практикой на примерах рабочих задач, в котором вы можете учиться в любое удобное время 24/7. Вы получите реальный опыт, разрабатывая качественный код и анализируя реальные данные.