Лучший тип вывода и методы кодирования для функций __repr __ ()?

В последнее время у меня было много проблем с __repr__(), format() и кодировки. Должен ли кодированный код __repr__() быть строкой в ​​кодировке Юникод? Есть ли лучшая кодировка для результата __repr__() в Python? То, что я хочу вывести, имеет символы не ASCII.

Я использую Python 2.x и хочу написать код, который можно легко адаптировать к Python 3. Таким образом, программа использует

# -*- coding: utf-8 -*-
from __future__ import unicode_literals, print_function  # The 'Hello' literal represents a Unicode object

Вот некоторые дополнительные проблемы, которые беспокоили меня, и я ищу решение, которое их решает:

  1. Должна работать печать на терминал UTF-8 (у меня sys.stdout.encoding установлено на UTF-8, но было бы лучше, если бы работали и другие случаи).
  2. Передача вывода в файл (закодированный в UTF-8) должна работать (в этом случае sys.stdout.encoding равно None) литий>
  3. Мой код для многих функций __repr__() в настоящее время содержит множество return ….encode('utf-8'), и это тяжело. Есть ли что-нибудь крепкое и легкое?
  4. В некоторых случаях у меня даже бывают такие уродливые звери, как return ('<{}>'.format(repr(x).decode('utf-8'))).encode('utf-8'), т. е. представление объектов декодируется, помещается в строку форматирования , а затем перекодировать. Я хотел бы избежать таких запутанных преобразований.

Что бы вы порекомендовали сделать для написания простых функций __repr__(), которые хорошо работают с этими вопросами кодирования?

65 голосов | спросил Eric O Lebigot 2 ndEurope/Moscowp30Europe/Moscow09bEurope/MoscowThu, 02 Sep 2010 17:57:16 +0400 2010, 17:57:16

3 ответа


0

В Python2 __repr____str__) должен возвращать строковый объект, а не Unicode объект. В Python3 ситуация обратная: __repr__ и __str__

class Foo(object):
    def __repr__(self):
        return u'\N{WHITE SMILING FACE}' 

class Bar(object):
    def __repr__(self):
        return u'\N{WHITE SMILING FACE}'.encode('utf8')

repr(Bar())
# ☺
repr(Foo())
# UnicodeEncodeError: 'ascii' codec can't encode character u'\u263a' in position 0: ordinal not in range(128)

В Python2 у вас нет выбора. Вы должны выбрать кодировку для возвращаемое значение __repr__.

Кстати, читали ли вы PrintFails вики ? Это может не отвечать напрямую другие ваши вопросы, но я нашел, что это полезно для освещения, почему некоторые ошибки возникают.


При использовании from __future__ import unicode_literals,

'<{}>'.format(repr(x).decode('utf-8'))).encode('utf-8')

можно проще записать как

str('<{}>').format(repr(x))

при условии, что str кодируется в utf-8 в вашей системе.

Без from __future__ import unicode_literals выражение можно записать в виде:

'<{}>'.format(repr(x))
ответил unutbu 2 ndEurope/Moscowp30Europe/Moscow09bEurope/MoscowThu, 02 Sep 2010 18:01:23 +0400 2010, 18:01:23
0

Я думаю, что декоратор может в разумной степени справиться с __repr__ Вот что я использую:

from __future__ import unicode_literals, print_function
import sys

def force_encoded_string_output(func):

    if sys.version_info.major < 3:

        def _func(*args, **kwargs):
            return func(*args, **kwargs).encode(sys.stdout.encoding or 'utf-8')

        return _func

    else:
        return func


class MyDummyClass(object):

    @force_encoded_string_output
    def __repr__(self):
        return 'My Dummy Class! \N{WHITE SMILING FACE}'
ответил Titon 13 ThuEurope/Moscow2012-12-13T01:10:09+04:00Europe/Moscow12bEurope/MoscowThu, 13 Dec 2012 01:10:09 +0400 2012, 01:10:09
0

Я использую функцию, подобную следующей:

def stdout_encode(u, default='UTF8'):
    if sys.stdout.encoding:
        return u.encode(sys.stdout.encoding)
    return u.encode(default)

Тогда мои функции __repr__ выглядят так:

def __repr__(self):
    return stdout_encode(u'<MyClass {0} {1}>'.format(self.abcd, self.efgh))
ответил Buttons840 17 Maypm12 2012, 19:59:59

Похожие вопросы

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132