2016-10-04 1 views
3

PEP-263 указывает, что кодировка указана в источнике применяется в следующем порядке:Как кодирование источника применяется в строковых литералах?

  1. read the file

  2. decode it into Unicode assuming a fixed per-file encoding

  3. convert it into a UTF-8 byte string

  4. tokenize the UTF-8 content

  5. compile it, creating Unicode objects from the given Unicode data and creating string objects from the Unicode literal data by first reencoding the UTF-8 data into 8-bit string data using the given file encoding

Итак, если я возьму этот код:

print 'abcdefgh' 
print u'abcdefgh' 

и преобразовать его в ROT-13:

# coding: rot13 

cevag 'nopqrstu' 
cevag h'nopqrstu' 

Я ожидаю, что он будет сначала декодирован, а затем станет идентичным оригиналу, печать:

abcdefgh 
abcdefgh 

Но вместо этого, он печатает:

nopqrstu 
abcdefgh 

Итак, unicode буквальные работает как expeced, но str остается непрореагировавший. Почему?


Упразднение некоторые возможности:

Я подтвердил, что проблема не в более позднем этапе (печать на консоль), но сразу же при разборе, becuase этот код производит «ValueError: неподдерживаемый формат символ «д» (0x71) с индексом 1":

x = '%q' % 1 # that is %d ! 

ответ

1

Я думаю, последняя точка на самом деле объясняет, что происходит довольно точно:

  1. compile it, creating Unicode objects from the given Unicode data and creating string objects from the Unicode literal data by first reencoding the UTF-8 data into 8-bit string data using the given file encoding

После первых 4 шагов, содержимое исходного файла являются Разбивается на лексемы версии Юникода из следующей строки:

print 'abcdefgh' 
print u'abcdefgh' 

После этого, на этапе 5, объект Строка 'abcdefgh' является перекодировать в 8-битные данные строки, используя заданную кодировку файла (который rot13), поэтому содержимое стать:

print 'nopqrstu' 
print u'abcdefgh' 
+0

ли вы ответить на 2 года позже клюв ause Я только что добавил ваш вопрос в мой любимый сегодня? Я думал об этом несколько часов назад и тестировал на своем терминале, и бум! ответ. В любом случае, спасибо. Я пришел сюда в первую очередь, потому что пытался понять, что означал шаг 5. – Maggyero

+0

@ Maggyero Да, я получил уведомление об этом вопросе и решил, что знаю ответ: D – zvone

+0

Итак, подведем итоги (исправьте меня, если я ошибаюсь): токенизатор принимает только строки UTF-8 в качестве входных данных. Поэтому исходный код должен быть перекодирован в UTF-8, то есть декодирован из объявленного кодирования исходного кода и закодирован в UTF-8. Однако * байтовые строковые литералы * в исходном коде также будут декодироваться в процессе, хотя они не должны (но на данном этапе мы еще не знаем их класс), так как они являются буквальными. Вот почему на шаге 5 они перекодируются в объявленную кодировку исходного кода. Кстати, последнее, что остается неясным, каков вывод токенизатора: строки Unicode или UTF-8? – Maggyero

 Смежные вопросы

  • Нет связанных вопросов^_^