Строковое кодирование и декодирование возможно из latin1 и utf8
Недавно я наткнулся на базу данных MySQL, которая была закодирована с использованием Latin1 и выполняла рендеринг при просмотре в символах вопросительного знака браузера. Чтобы исправить это, мы изменили кодировку DB на utf8 и Collation на utf8_general_ci во всех наших таблицах, но уже сохраненные данные все еще показывались с символами вопросительного знака, все хранение и опрос данных из mysql в браузер это было сделано php, я удостоверился, что utf8 использовался и на php, и даже запускал сетевые имена utf8, как многие предлагали в Интернете, проблема в том, что теперь у меня появились странные символы, такие как Ã Â, в строках, которые, как мы знали, не имели их,
Примеры данных
Хранится:
EMMANUEL PE \ xc3 \xc2\u2018A ГОМЕС ПОРТУГАЛИЯ
Вынесено:
ЭММАНУЭЛЬ ПЕВАЯ ГОМЕС ПОРТУГАЛИЯ
Надлежащая:
ЭММАНУЭЛЬ ПЕНЬЯ ГОМЕС ПОРТУГАЛИЯ
Хранится:
Луис Херн \xe1ndez-Higareda
Вынесено:
Луис Эрнандес-Хигареда
Надлежащая:
Луис Эрнандес-Хигареда
Хранится:
Тереза де Хес \xc3\u0192\xc2\xbas Галисия G\xc3\u0192\xc2\xb3mez
Вынесено:
Тереза де Хесус Галисия Гемес
Надлежащая:
Тереза Хесус Галисия Гомес
Хранится:
DR. JOS \ xc3 \ u0192 \ xc2 \ u2030 ABEN \ xc3 \ u0192 \ xc2 \ x81MAR RIC \ xc3 \ u0192 \ xc2 \ x81RDEZ GARC \ xc3 \ u0192 \ xc2 \ x8dA
Надлежащая:
DR. Хосе Абенмар Ричардез Гарса
В настоящее время я использую Python для получения данных из БД, я пытаюсь нормализовать Unicode UTF8, но я действительно потерян, вот, насколько я здесь, мне нужно преобразовать то, что в настоящее время выглядит как странно символы для читаемого текста, как показано выше.
что мне здесь не хватает? данные о неисправимом?
Функции https://gist.github.com/2649463
Примечание: из всех примеров есть 1, который правильно отображает (оставлено там, поэтому следует принять во внимание, если дан какой-либо совет, как это исправить)
2 ответа
Если вы попытались вставить символы, которые не могут быть представлены в latin1
в столбцы, хранящиеся под этой кодировкой символов, эти символы были бы необратимо заменены на ?
- информация была потеряна: ваш единственный вариант - переустановить / обновить данные теперь, когда столбец хранится в utf8
,
Однако некоторые данные в вашем вопросе не имеют большого смысла. Например:
Хранится:
EMMANUEL PE \ xc3 \ xc2\u2018A ГОМЕС ПОРТУГАЛИЯ
Вы пытаетесь показать байты или символы, которые в настоящее время хранятся? В любом случае, один из \u
или же \x
escape-коды не имеют смысла.
Вы говорите, что исходные данные были закодированы как latin1
; в этом наборе символов символ С кодируется как 0xd1
, Вы говорите, что затем преобразовали данные в utf8
, который изменил бы кодировку этого символа на двухбайтовую последовательность 0xc391
(который объясняет \xc3
вы показываете как хранящийся выше; Однако, не ясно, как второй байт 0x91
превратился в последовательность \u0192\xc2\u2018
в вашем фрагменте *).
Я подозреваю, что на самом деле данные были подвергнуты дальнейшим преобразованиям, возможно, между тем, что в настоящее время хранится, и какими-либо средствами, которые вы используете для просмотра такого хранилища. Вам было бы полезно сначала выяснить , что именно хранится в вашей базе данных:
SELECT HEX(my_column) FROM my_table WHERE ...
Как только это будет определено, вы сможете лучше понять, какие преобразования (если таковые имеются) необходимо использовать для хранения ваших данных, чтобы сделать их utf8
и какие нежелательные преобразования (если таковые имеются) происходят во время операций хранения и поиска.
* Теперь, прочитав ответ Танасиса Петса, я понял, что он понял, что вы, кажется, правильно расшифровали utf8
закодированные строки как latin1
закодировал полученные символы используя utf8
а затем декодировать эти байты как latin1
снова. Это действительно создает последовательности символов, которые вы показали, но все же необходимо понять, что на самом деле хранится и что происходит из-за преобразований во время поиска.
Попробуй это:
print str.encode('cp1252').decode('utf-8').encode('cp1252').decode('utf-8')
пример использования ipython
:
In [49]: a=u'Teresa de Jes\xc3\u0192\xc2\xbas Galicia G\xc3\u0192\xc2\xb3mez'
In [50]: a=u'Teresa de Jes\xc3\u0192\xc2\xbas Galicia G\xc3\u0192\xc2\xb3mez'
In [51]: print a
Teresa de Jesús Galicia Gómez
In [52]: print a.encode('cp1252').decode('utf-8').encode('cp1252').decode('utf-8')
Teresa de Jesús Galicia Gómez
Это "неправильно закодированный" utf-8..