Предположим на мгновение, что нельзя использовать print (и, таким образом, воспользоваться возможностью автоматического обнаружения кодирования). Итак, это оставляет нас с sys.stdout. Тем не менее, sys.stdout настолько тупо, что не делает никакого разумного кодирования.
Теперь читаем страницу вики Python PrintFails и отправляем попробовать следующий код:
$ python -c 'import sys, codecs, locale; print str(sys.stdout.encoding); \
sys.stdout = codecs.getwriter(locale.getpreferredencoding())(sys.stdout);
Однако это тоже не работает (по крайней мере, на Mac). Слишком понятно, почему:
>>> import locale
>>> locale.getpreferredencoding()
'mac-roman'
>>> sys.stdout.encoding
'UTF-8'
(UTF-8 - это то, что понимает один терминал).
Таким образом, один из приведенных выше вариантов кода:
$ python -c 'import sys, codecs, locale; print str(sys.stdout.encoding); \
sys.stdout = codecs.getwriter(sys.stdout.encoding)(sys.stdout);
И теперь строки unicode отправляются правильно на sys.stdout и, следовательно, правильно печатаются на терминале (sys.stdout подключен терминал).
Является ли это правильным способом записи строк в unicode в sys.stdout или я должен делать что-то еще?
РЕДАКТИРОВАТЬ: время от времени, скажем, при прокладке на выходе less - sys.stdout.encoding будет None. в этом случае вышеуказанный код не будет выполнен.