Какие различия между `format ()` и `str ()`? - PullRequest
1 голос
/ 01 июня 2019
>>> format(sys.stdout)
"<_io.TextIOWrapper name='<stdout>' mode='w' encoding='UTF-8'>"
>>> str(sys.stdout)
"<_io.TextIOWrapper name='<stdout>' mode='w' encoding='UTF-8'>"

Я не очень уверен в следующих цитатах из ссылок на библиотеки Python. Какие различия существуют между format() и str() или между object.__format__(self, format_spec) и object.__str__(self )? Когда мы будем использовать какие?

object.__str__(self )

Вызывается по str (объект) и встроенным функциям format () и print () вычислить «неформальное» или красиво печатаемое строковое представление объект.

object.__format__(self, format_spec)

Вызывается встроенной функцией format () и, соответственно, оценкой. форматированных строковых литералов и метода str.format (), чтобы получить «Отформатированное» строковое представление объекта.

1 Ответ

1 голос
/ 01 июня 2019

Я собираюсь разбить основные три (технически основные 2, потому что __format__ не очень часто реализуется).Я пройдусь по всем трем, а затем соберу все это в один хороший класс.


Наиболее распространенный __str__:

Вот как вы хотите представить этот объект какstr.Часто это менее детально, чем __repr__ и используется в основном для конечного пользователя.Например, если у нас есть класс person, мы можем реализовать str следующим образом:

class Person:
    def __init__(self, name="John Smith"):
        self.name = name
    def __str__(self):
        # This will return Hello my name is John Smith by default
        return f"Hello my name is {self.name}" 

Менее распространенный __repr__:

Если честно, я реализую этобольше, чем я реализую str для большинства проектов.Это должно возвращать представление объекта как str таким образом, чтобы оно было полезным для разработчика вместо конечного пользователя и вызывалось через repr(my_obj).Если класс не реализует магический метод __str__, то python попытается автоматически вызвать свой метод __repr__ при использовании str(my_obj) (таким образом, вы можете сначала реализовать repr и позже str).Часто repr класса возвращает способ воссоздания этого объекта, например:

class Person:
    def __init__(self, name="John Smith"):
        self.name = name
    def __repr__(self):
        return f"Person(name=\"{self.name}\")" 
p = Person()
print(str(p)) # Prints "Person(name="John Smith")"

Проклятый потомок __format__: [Я просто так его называю, потому что он используется так редко:)]

Чтобы понять это, я должен сначала объяснить некоторые вещи форматирования.Возможно, вы уже видели некоторые из этих вещей раньше или не видели.

Давайте используем фиктивный класс:

class Person:
    def __init__(self, name="John Smith", age=22):
        self.name = name
        self.age = age
    def __repr__(self):
        return f'Person(name="{self.name}", age={self.age})'
    def __str__(self):
        # This will return Hello my name is John Smith by default
        return str(self.name)
p = Person()
# This prints the str of p
print("{!s}".format(p)) # John Smith
# This prints the representation of p
print("{!r}".format(p)) # Person(name="John Smith", age=22)

Хорошо, так что вы можете отформатировать свой класс как str или как repr, но что, если вы хотите отформатировать его самостоятельно?путь?Большинству людей не нужно этого делать;но это сила Python, вы можете сделать что угодно .Мы можем создавать различные теги вместо r и s (хотя вместо 1010 * используется :):

class Person:
    def __init__(self, name="John Smith", age=22):
        self.name = name
        self.age = age
    def __repr__(self):
        return f'Person(name="{self.name}", age={self.age})'
    def __str__(self):
        # This will return Hello my name is John Smith by default
        return str(self.name)
    def __format__(self, format_spec):
        # Make sure to choose a word not currently used (i.e. don't pick s, r, etc.)
        if format_spec == 'age': # get a persons age
            return f"{self.name} is {self.age} years old"
        elif format_spec == 'birthday':
            return "Yesterday"
        return str(self) # A default case
p = Person()
# This prints the str of p
print("{!s}".format(p))
# This with representation of p
print("{!r}".format(p))
print("{:age}".format(p))
print("{:birthday}".format(p))
print(f"{p:age} and his birthday was {p:birthday}")

Очевидно, что это гораздо больше, чем могут ограничить мои ограниченные знанияно это должно быть хорошей общей областью:).

Есть некоторые пакеты, которые используют это, такие как datetime.Если вам интересно узнать больше о силе формата Pyformat , то вы можете легко это понять: PyFormat .

Отказ от ответственности:

У меня нетбольшой опыт использования __format__, поэтому я не могу предоставить хороший вариант использования (хотя вариант использования datetime не плохой).Здесь все просто для того, чтобы показать большую разницу между магическими методами str, repr и format.Если я что-то не так (особенно в случае использования __format__), пожалуйста, дайте мне знать, и я обновлю его.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...