При использовании «специальных» символов Unicode они выходят как странный мусор при кодировании JSON:
php > echo json_encode(['foo' => '馬']); {"foo":"\u99ac"}
Зачем? Я сделал что-то не так с моими кодировками?
(Это заданный вопрос, чтобы прояснить эту тему раз и навсегда, поскольку это возникает снова и снова.)
Прежде всего: здесь нет ничего плохого. Вот как символы могут быть закодированы в JSON. Он находится в официальном стандарте . Он основан на том, как строковые литералы могут быть сформированы в Javascript ECMAScript ( раздел 7.8.4 «Строковые литералы» ) и описывается как таковой:
Любая кодовая точка может быть представлена как шестнадцатеричное число. Значение такого числа определяется ISO / IEC 10646. Если кодовая точка находится на базовой многоязычной плоскости (U + 0000 – U + FFFF), то она может быть представлена в виде шестисимвольной последовательности: обратного солидуса, за которым следует строчная буква u, за которой следуют четыре шестнадцатеричные цифры, которые кодируют кодовую точку. […] Итак, например, строка, содержащая только один обратный символ солидуса, может быть представлена как «\ u005C».
Короче: любой символ может быть закодирован как \u....
, где ....
– это кодовая точка Юникода символа (или кодовая точка половины суррогатной пары UTF-16, для символов вне BMP) ,
"馬" "\u99ac"
Эти два строковых литерала представляют один и тот же символ, они абсолютно эквивалентны. Когда эти строковые литералы разбираются с помощью синтаксического анализатора JSON, они оба приведут к строке «馬». Они не выглядят одинаково, но они означают одно и то же в формате кодирования данных JSON.
json_encode
PHP предпочтительно кодирует символы, отличные от ASCII, с помощью \u....
escape-последовательностей. Технически это не обязательно, но это так. И результат совершенно верен. Если вы предпочитаете иметь буквальные символы в JSON вместо escape-последовательностей, вы можете установить флаг JSON_UNESCAPED_UNICODE
в PHP 5.4 или выше:
php > echo json_encode(['foo' => '馬'], JSON_UNESCAPED_UNICODE); {"foo":"馬"}
Чтобы подчеркнуть: это только предпочтение , не нужно каким-либо образом переносить «символы Юникода» в JSON.