UTF8?
UTF16?
Строки в PHP также отслеживают используемую кодировку?
Давайте посмотрим на этот скрипт для примера. Скажи, что я бегу:
$original = "शक्नोम्यत्तुम्";
Что на самом деле происходит?
Очевидно, я думаю $original
, не будет содержать только 7 символов. Эти глифы должны быть представлены несколькими байтами.
Тогда я делаю:
$converted = mb_convert_encoding ($original , "UTF-8");
Что будет с $converted
? Как будет $converted
отличаться от $original
?
Будет ли это точно такая же последовательность байтов, $original
но с другой кодировкой?
Ответы:
Строка PHP - это просто последовательность байтов, без какой-либо кодировки. Строковые значения могут поступать из различных источников: клиента (через HTTP), базы данных, файла или из строковых литералов в вашем исходном коде. PHP читает все это как байтовые последовательности и никогда не извлекает никакой информации о кодировке.
Пока все ваши источники данных и места назначения используют одну и ту же кодировку, самое худшее, что может случиться, это неправильные позиции строк (если вы используете многобайтовые кодировки), поскольку PHP будет считать байты, а не символы.
Но если кодировки не совпадают (например, вы записываете строковый литерал в исходный файл, сохраненный как UTF-8, а затем отправляете его в базу данных, которая ожидает Latin-1), PHP не выполнит для вас никакого преобразования: счастливо скопировать байты по сырью.
Самое разумное решение:
Content-type
заголовки).SET NAMES UTF8
в MySQL).Почему UTF-8? Поскольку он может представлять все символы Unicode и, таким образом, заменяет все существующие 7-разрядные и 8-разрядные кодировки, а также потому, что он двоично совместим с ASCII, то есть каждая допустимая строка ASCII также является допустимой строкой UTF-8 (но не vv .).
В вашем примере, что происходит, это.
Сначала вы сохраняете свой исходный файл; ваш текстовый редактор, вероятно, настроен на использование UTF-8, поэтому ваш строковый литерал заканчивается в кодировке UTF-8 на диске. PHP читает этот файл, интерпретируя строку как последовательность байтов;
$original
теперь содержит строку из 7 символов в кодировке UTF-8, которая представляет собой последовательность байтов (хотя она содержит более 7 байтов, поскольку каждый символ представлен двумя или более байтами). Если вы затем позвонитеecho $original
, закодированная строка будет отправлена клиенту как есть; если вы сказали клиенту ожидать UTF-8, все в порядке, но если нет, PHP не сможет определить разницу, и вы получите мусор в браузере. В качестве эксперимента попробуйте это:strlen
не зависит от кодировки и предполагает 8-битное кодирование с фиксированной шириной, то есть один байт на символ, поэтому он будет считать байты, а не символы.источник