pprint — Красивый вывод данных
Исходный код: Lib/pprint.py
Модуль pprint предоставляет возможность «красивого вывода» произвольных структур данных Python в формате, который можно использовать в качестве входных данных для интерпретатора. Если форматируемые структуры содержат объекты, которые не являются фундаментальными типами Python, представление может быть не загружаемым. Это может быть в случае, если включены объекты, такие как файлы, сокеты или классы, а также многие другие объекты, которые не могут быть представлены как литералы Python.
Форматированное представление сохраняет объекты на одной строке, если это возможно, и разбивает их на несколько строк, если они не помещаются в разрешенную ширину. Явно создавайте объекты PrettyPrinter, если вам нужно настроить ограничение по ширине.
Словари сортируются по ключу перед вычислением отображения.
Изменено в версии 3.9: Добавлена поддержка красивого вывода types.SimpleNamespace.
Изменено в версии 3.10: Добавлена поддержка красивого вывода dataclasses.dataclass.
Модуль pprint определяет один класс:
-
class pprint.PrettyPrinter(indent=1, width=80, depth=None, stream=None, *, compact=False, sort_dicts=True, underscore_numbers=False) -
Создает экземпляр
PrettyPrinter. Этот конструктор понимает несколько ключевых параметров.stream (по умолчанию
sys.stdout) — это объект, подобный файлу, в который будет выводиться результат вызова его методаwrite().Другие значения конфигурируют способ отображения вложенности сложных структур данных.
indent (по умолчанию 1) задаёт количество отступов для каждого уровня вложенности.
depth управляет количеством уровней вложенности, которые могут быть выведены; если структура данных, которая выводится, слишком глубока, следующий вложенный уровень заменяется на
.... По умолчанию нет ограничений на глубину форматируемых объектов.width (по умолчанию 80) задаёт желаемое максимальное количество символов на строке в выводе. Если структуру невозможно отформатировать в рамках ограничения по ширине, будет сделана попытка.
compact влияет на способ форматирования длинных последовательностей (списков, кортежей, множеств и т. д.). Если compact ложно (по умолчанию), каждый элемент последовательности будет отформатирован на отдельной строке. Если compact истинно, то столько элементов, сколько поместится в width, будут отформатированы на каждой строке вывода.
Если sort_dicts истинно (по умолчанию), словари будут отформатированы с отсортированными ключами, в противном случае они будут отображаться в порядке вставки.
Если underscore_numbers истинно, целые числа будут отформатированы с символом
_для разделителя тысяч, в противном случае нижние подчеркивания не отображаются (по умолчанию).Изменено в версии 3.4: Добавлен параметр compact.
Изменено в версии 3.8: Добавлен параметр sort_dicts.
Изменено в версии 3.10: Добавлен параметр underscore_numbers.
>>> import pprint >>> stuff = ['spam', 'eggs', 'lumberjack', 'knights', 'ni'] >>> stuff.insert(0, stuff[:]) >>> pp = pprint.PrettyPrinter(indent=4) >>> pp.pprint(stuff) [ ['spam', 'eggs', 'lumberjack', 'knights', 'ni'], 'spam', 'eggs', 'lumberjack', 'knights', 'ni'] >>> pp = pprint.PrettyPrinter(width=41, compact=True) >>> pp.pprint(stuff) [['spam', 'eggs', 'lumberjack', 'knights', 'ni'], 'spam', 'eggs', 'lumberjack', 'knights', 'ni'] >>> tup = ('spam', ('eggs', ('lumberjack', ('knights', ('ni', ('dead', ... ('parrot', ('fresh fruit',)))))))) >>> pp = pprint.PrettyPrinter(depth=6) >>> pp.pprint(tup) ('spam', ('eggs', ('lumberjack', ('knights', ('ni', ('dead', (...)))))))
Модуль pprint также предоставляет несколько функций-«обходных путей»:
-
pprint.pformat(object, indent=1, width=80, depth=None, *, compact=False, sort_dicts=True, underscore_numbers=False) -
Возвращает отформатированное представление object в виде строки. indent, width, depth, compact, sort_dicts и underscore_numbers будут переданы конструктору
PrettyPrinterв качестве параметров форматирования.Изменено в версии 3.4: Добавлен параметр compact.
Изменено в версии 3.8: Добавлен параметр sort_dicts.
Изменено в версии 3.10: Добавлен параметр underscore_numbers.
-
pprint.pp(object, *args, sort_dicts=False, **kwargs) -
Выводит отформатированное представление object, за которым следует перевод строки. Если sort_dicts ложно (по умолчанию), словари будут отображаться с ключами в порядке вставки, в противном случае ключи словарей будут отсортированы. args и kwargs будут переданы модулю
pprint()в качестве параметров форматирования.Введено в версии 3.8.
-
pprint.pprint(object, stream=None, indent=1, width=80, depth=None, *, compact=False, sort_dicts=True, underscore_numbers=False) -
Выводит отформатированное представление object в stream, за которым следует перевод строки. Если stream это
None, используетсяsys.stdout. Это можно использовать в интерактивном интерпретаторе вместо функцииprint()для проверки значений (вы даже можете переназначитьprint = pprint.pprintдля использования в области видимости). indent, width, depth, compact, sort_dicts и underscore_numbers будут переданы конструкторуPrettyPrinterв качестве параметров форматирования.Изменено в версии 3.4: Добавлен параметр compact.
Изменено в версии 3.8: Добавлен параметр sort_dicts.
Изменено в версии 3.10: Добавлен параметр underscore_numbers.
>>> import pprint >>> stuff = ['spam', 'eggs', 'lumberjack', 'knights', 'ni'] >>> stuff.insert(0, stuff) >>> pprint.pprint(stuff) [<Recursion on list with id=...>, 'spam', 'eggs', 'lumberjack', 'knights', 'ni']
-
pprint.isreadable(object) -
Определяет, является ли отформатированное представление object «читаемым» или может быть использовано для восстановления значения с помощью
eval(). Это всегда возвращаетFalseдля рекурсивных объектов.>>> pprint.isreadable(stuff) False
-
pprint.isrecursive(object) -
Определяет, требует ли object рекурсивное представление.
Также определена ещё одна вспомогательная функция:
-
pprint.saferepr(object) -
Возвращает строковое представление object, защищённое от рекурсивных структур данных. Если представление object содержит рекурсивную ссылку, рекурсивная ссылка будет представлена как
<Recursion on typename with id=number>. Представление не форматируется иначе.>>> pprint.saferepr(stuff) "[<Recursion on list with id=...>, 'spam', 'eggs', 'lumberjack', 'knights', 'ni']"
Объекты PrettyPrinter
PrettyPrinter имеют следующие методы:
-
PrettyPrinter.pformat(object) -
Возвращает отформатированное представление объекта object. Это учитывает параметры, переданные конструктору
PrettyPrinter.
-
PrettyPrinter.pprint(object) -
Выводит отформатированное представление объекта object в заданный поток, после чего переходит на новую строку.
Следующие методы предоставляют реализацию соответствующих функций с одинаковыми именами. Использование этих методов на экземпляре немного эффективнее, так как не требуется создание новых объектов PrettyPrinter.
-
PrettyPrinter.isreadable(object) -
Определяет, является ли отформатированное представление объекта «читаемым» или может быть использовано для восстановления значения с помощью
eval(). Обратите внимание, что для рекурсивных объектов это возвращаетFalse. Если параметр depth объектаPrettyPrinterустановлен и объект глубже, чем разрешено, это возвращаетFalse.
-
PrettyPrinter.isrecursive(object) -
Определяет, требует ли объект рекурсивного представления.
Этот метод предоставляется в качестве плагина, позволяющего подклассам изменять способ преобразования объектов в строки. По умолчанию используется внутренняя реализация saferepr().
-
PrettyPrinter.format(object, context, maxlevels, level) -
Возвращает три значения: отформатированную версию объекта object в виде строки, флаг, указывающий, является ли результат читаемым, и флаг, указывающий, была ли обнаружена рекурсия. Первый аргумент — объект, который нужно представить. Второй — словарь, содержащий
id()объектов, которые являются частью текущего контекста представления (прямых и косвенных контейнеров для object, влияющих на представление), как ключи; если необходимо представить объект, уже представленный в context, третье возвращаемое значение должно бытьTrue. Рекурсивные вызовы методаformat()должны добавлять дополнительные записи для контейнеров в этот словарь. Третий аргумент, maxlevels, задаёт требуемый предел рекурсии; он будет0если предел не задан. Этот аргумент следует передавать неизменённым в рекурсивных вызовах. Четвёртый аргумент, level, задаёт текущий уровень; рекурсивные вызовы должны передавать значение меньшее, чем значение текущего вызова.
Пример
Для демонстрации нескольких способов использования функции pprint() и её параметров давайте получим информацию о проекте с PyPI:
>>> import json
>>> import pprint
>>> from urllib.request import urlopen
>>> with urlopen('https://pypi.org/pypi/sampleproject/json') as resp:
... project_info = json.load(resp)['info']
В базовом виде pprint() отображает весь объект:
>>> pprint.pprint(project_info)
{'author': 'The Python Packaging Authority',
'author_email': 'pypa-dev@googlegroups.com',
'bugtrack_url': None,
'classifiers': ['Development Status :: 3 - Alpha',
'Intended Audience :: Developers',
'License :: OSI Approved :: MIT License',
'Programming Language :: Python :: 2',
'Programming Language :: Python :: 2.6',
'Programming Language :: Python :: 2.7',
'Programming Language :: Python :: 3',
'Programming Language :: Python :: 3.2',
'Programming Language :: Python :: 3.3',
'Programming Language :: Python :: 3.4',
'Topic :: Software Development :: Build Tools'],
'description': 'A sample Python project\n'
'=======================\n'
'\n'
'This is the description file for the project.\n'
'\n'
'The file should use UTF-8 encoding and be written using '
'ReStructured Text. It\n'
'will be used to generate the project webpage on PyPI, and '
'should be written for\n'
'that purpose.\n'
'\n'
'Typical contents for this file would include an overview of '
'the project, basic\n'
'usage examples, etc. Generally, including the project '
'changelog in here is not\n'
'a good idea, although a simple "What\'s New" section for the '
'most recent version\n'
'may be appropriate.',
'description_content_type': None,
'docs_url': None,
'download_url': 'UNKNOWN',
'downloads': {'last_day': -1, 'last_month': -1, 'last_week': -1},
'home_page': 'https://github.com/pypa/sampleproject',
'keywords': 'sample setuptools development',
'license': 'MIT',
'maintainer': None,
'maintainer_email': None,
'name': 'sampleproject',
'package_url': 'https://pypi.org/project/sampleproject/',
'platform': 'UNKNOWN',
'project_url': 'https://pypi.org/project/sampleproject/',
'project_urls': {'Download': 'UNKNOWN',
'Homepage': 'https://github.com/pypa/sampleproject'},
'release_url': 'https://pypi.org/project/sampleproject/1.2.0/',
'requires_dist': None,
'requires_python': None,
'summary': 'A sample Python project',
'version': '1.2.0'}
Результат можно ограничить определённой глубиной (для более глубоких содержимого используется многоточие):
>>> pprint.pprint(project_info, depth=1)
{'author': 'The Python Packaging Authority',
'author_email': 'pypa-dev@googlegroups.com',
'bugtrack_url': None,
'classifiers': [...],
'description': 'A sample Python project\n'
'=======================\n'
'\n'
'This is the description file for the project.\n'
'\n'
'The file should use UTF-8 encoding and be written using '
'ReStructured Text. It\n'
'will be used to generate the project webpage on PyPI, and '
'should be written for\n'
'that purpose.\n'
'\n'
'Typical contents for this file would include an overview of '
'the project, basic\n'
'usage examples, etc. Generally, including the project '
'changelog in here is not\n'
'a good idea, although a simple "What\'s New" section for the '
'most recent version\n'
'may be appropriate.',
'description_content_type': None,
'docs_url': None,
'download_url': 'UNKNOWN',
'downloads': {...},
'home_page': 'https://github.com/pypa/sampleproject',
'keywords': 'sample setuptools development',
'license': 'MIT',
'maintainer': None,
'maintainer_email': None,
'name': 'sampleproject',
'package_url': 'https://pypi.org/project/sampleproject/',
'platform': 'UNKNOWN',
'project_url': 'https://pypi.org/project/sampleproject/',
'project_urls': {...},
'release_url': 'https://pypi.org/project/sampleproject/1.2.0/',
'requires_dist': None,
'requires_python': None,
'summary': 'A sample Python project',
'version': '1.2.0'}
Кроме того, можно указать максимальную ширину символов width. Если длинный объект нельзя разбить, указанная ширина будет превышена:
>>> pprint.pprint(project_info, depth=1, width=60)
{'author': 'The Python Packaging Authority',
'author_email': 'pypa-dev@googlegroups.com',
'bugtrack_url': None,
'classifiers': [...],
'description': 'A sample Python project\n'
'=======================\n'
'\n'
'This is the description file for the '
'project.\n'
'\n'
'The file should use UTF-8 encoding and be '
'written using ReStructured Text. It\n'
'will be used to generate the project '
'webpage on PyPI, and should be written '
'for\n'
'that purpose.\n'
'\n'
'Typical contents for this file would '
'include an overview of the project, '
'basic\n'
'usage examples, etc. Generally, including '
'the project changelog in here is not\n'
'a good idea, although a simple "What\'s '
'New" section for the most recent version\n'
'may be appropriate.',
'description_content_type': None,
'docs_url': None,
'download_url': 'UNKNOWN',
'downloads': {...},
'home_page': 'https://github.com/pypa/sampleproject',
'keywords': 'sample setuptools development',
'license': 'MIT',
'maintainer': None,
'maintainer_email': None,
'name': 'sampleproject',
'package_url': 'https://pypi.org/project/sampleproject/',
'platform': 'UNKNOWN',
'project_url': 'https://pypi.org/project/sampleproject/',
'project_urls': {...},
'release_url': 'https://pypi.org/project/sampleproject/1.2.0/',
'requires_dist': None,
'requires_python': None,
'summary': 'A sample Python project',
'version': '1.2.0'}
© 2001–2023 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.10/library/pprint.html