@Kamikaze

Как правильно использовать юникод в python 2.7?

Что-то странное происходит, вероятнее всего из-за того, что я что-то не понимаю, потому прошу помощи:
Продолжение истории с journalctl древней версии, который в формате json отдает вместо кириллицы вот такое:
"MESSAGE" : "2017-11-28 20:16:06.015  INFO 19853 --- [enerContainer-1] r.p.e.s.i.m.h.s.l.LocalMszPackageHandler : [MSG=d182a0ea-d45f-11e7-a390-7f0ad09e8f90] \uffffffd0\uffffffa1\uffffffd0\uffffffbe\uffffffd1\uffffff85\uffffffd1\uffffff80\uffffffd0\uffffffb0\uffffffd0\uffffffbd\uffffffd0\uffffffb5\uffffffd0\uffffffbd\uffffffd0\uffffffb8\uffffffd0\uffffffb5 \uffffffd0\uffffffbf\uffffffd0\uffffffb0\uffffffd0\uffffffba\uffffffd0\uffffffb5\uffffffd1\uffffff82\uffffffd0\uffffffb0"

Несложными логическими выводами понимаем что re.sub('uffffff','x',line) дает нам уже нормальный UTF-8.
Далее методом волшебных костылей имеем следующее:
>>> line2 = "\xd0\x9e\xd1\x82\xd0\xbf\xd1\x80\xd0\xb0\xd0\xb2\xd0\xba\xd0\xb0 \xd0\xbf\xd0\xbe\xd0\xb4\xd1\x82\xd0\xb2\xd0\xb5\xd1\x80\xd0\xb6\xd0\xb4\xd0\xb5\xd0\xbd\xd0\xb8\xd1\x8f \xd0\xbf\xd1\x83\xd0\xb1\xd0\xbb\xd0\xb8\xd0\xba\xd0\xb0\xd1\x86\xd0\xb8\xd0\xb8"
>>> unicode(line2)
u'\u041e\u0442\u043f\u0440\u0430\u0432\u043a\u0430 \u043f\u043e\u0434\u0442\u0432\u0435\u0440\u0436\u0434\u0435\u043d\u0438\u044f \u043f\u0443\u0431\u043b\u0438\u043a\u0430\u0446\u0438\u0438'
>>> lined = unicode(line2)
>>> print lined
Отправка подтверждения публикации


Казалось бы, шикарно, пишем тестовый код:

...
line = re.sub('uffffff','x',line)
patterns_object = re.search('(((\\\\x[a-f,0-9]{2})+\s*)+)',line)	
if patterns is not None:                                       
    line2 = patterns.group(0)                  
    line3 = unicode(line2)
    print "line:" + line
    print "line3:" + line3


И имеем на выходе что-то мало напоминающее то, что было выше:
line:\xd0\x9e\xd1\x82\xd0\xbf\xd1\x80\xd0\xb0\xd0\xb2\xd0\xba\xd0\xb0 \xd0\xbf\xd0\xbe\xd0\xb4\xd1\x82\xd0\xb2\xd0\xb5\xd1\x80\xd0\xb6\xd0\xb4\xd0\xb5\xd0\xbd\xd0\xb8\xd1\x8f \xd0\xbf\xd1\x83\xd0\xb1\xd0\xbb\xd0\xb8\xd0\xba\xd0\xb0\xd1\x86\xd0\xb8\xd0\xb8 \xd0\xb2 \xd0\x9f\xd0\x9d\xd0\xa1\xd0\x98

line3:\xd0\x9e\xd1\x82\xd0\xbf\xd1\x80\xd0\xb0\xd0\xb2\xd0\xba\xd0\xb0 \xd0\xbf\xd0\xbe\xd0\xb4\xd1\x82\xd0\xb2\xd0\xb5\xd1\x80\xd0\xb6\xd0\xb4\xd0\xb5\xd0\xbd\xd0\xb8\xd1\x8f \xd0\xbf\xd1\x83\xd0\xb1\xd0\xbb\xd0\xb8\xd0\xba\xd0\xb0\xd1\x86\xd0\xb8\xd0\xb8 \xd0\xb2 \xd0\x9f\xd0\x9d\xd0\xa1\xd0\x98


Опробовал найденные варианты вида print(str(b)), print(unicode(b)), print(repr(b)), всё равно одно и то же.

Тыкнете носом в чем я не разобрался и что идти читать?
  • Вопрос задан
  • 749 просмотров
Решения вопроса 2
@Fixid
Лучше просто перейдите на python3, это менее болезненно
Ответ написан
@Kamikaze Автор вопроса
Если кому интересно, в 2.7 решил примерно вот таким вот костылем:
...
def _repl_unicode(matchobj):
	line3 = re.sub('\\\\uffffff','',matchobj.group(0))
	line4 = binascii.unhexlify(line3)
	return line4

while True:
	line2_obj = re.search('((\\\\uffffff[0-9a-f]{2}){2})',line)
	if line2_obj is not None:
		line2 = line2_obj.group(0)
		line3 = re.sub('\\\\uffffff','',line2)
		line = re.sub('((\\\\uffffff[0-9a-f]{2}){2})',_repl_unicode,line)
	else:
		break
...

И вуаля, на выходе уже вполне себе нормальная кириллица.
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
@asd111
Переходи на python 3. Потому что 2.7 не будет поддерживаться после 2020.
Numpy уже не обновляют для 2.7 и django тоже.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы