Unicode-символы в Ruby-скрипте? - PullRequest
8 голосов
/ 14 августа 2010

Я хотел бы написать скрипт на Ruby, который записывает японские символы в консоль. Например:

puts "こんにちは・今日は"

Однако при его запуске я получаю исключение:

jap.rb:1: Invalid char `\377' in expression
jap.rb:1: Invalid char `\376' in expression

Возможно ли это сделать? Я использую Ruby 1.8.6.

1 Ответ

12 голосов
/ 14 августа 2010

Вы сохранили файл в кодировке UTF-16LE, которую Windows вводит в заблуждение «Unicode». Этого кодирования, как правило, лучше избегать, поскольку оно не является ASCII-надмножеством: каждая единица кода хранится в виде двух байтов, а символы ASCII, а другой байт хранится как \0. Это запутает очень много программного обеспечения; необычно использовать UTF-16 для хранения файлов.

То, что вы видите с \377 и \376 (восьмеричное для \xFF и \xFE), представляет собой последовательность меток порядка байтов U + FEFF, помещенную в начале файлов UTF-16, чтобы отличить UTF-16LE от UTF-16BE.

Ruby 1.8 полностью основан на байтах; он не пытается читать символы Юникода из скрипта. Таким образом, вы можете сохранять исходные файлы только в ASCII-совместимых кодировках. Обычно вы хотите сохранить свои файлы как UTF-8 (без спецификации; поддельная спецификация UTF-8 - еще одно замечательное новшество Microsoft, которое ломает все). Это отлично подойдет для сценариев в Интернете, создающих страницы UTF-8.

И если вы хотите быть уверенными, что исходный код будет допустимым для сохранения в любой ASCII-совместимой кодировке, вы можете закодировать строку, чтобы сделать ее более устойчивой (если она менее читаема):

puts "\xe3\x81\x93\xe3\x82\x93\xe3\x81\xab\xe3\x81\xa1\xe3\x81\xaf\xe3\x83\xbb\xe4\xbb\x8a\xe6\x97\xa5\xe3\x81\xaf"

Тем не менее! Запись на консоль сама по себе является большой проблемой. Какая кодировка используется для отправки символов на консоль, зависит от платформы к платформе. В Linux или OS X это UTF-8. В Windows это разные кодировки для каждой локали установки (как указано в разделе «Язык для приложений, не поддерживающих Юникод» в разделе панели управления «Язык и региональные стандарты»), но это никогда UTF-8. Этот параметр, опять-таки вводящий в заблуждение, известен как кодовая страница ANSI.

Так что, если вы используете японскую установку Windows, вашей консольной кодировкой будет кодовая страница Windows 932 (вариант Shift-JIS). Если это так, вы можете сохранить текстовый файл из текстового редактора, используя «ANSI» или явно «японский cp932», и когда вы запустите его в Ruby, вы получите правильные символы. Опять же, если вы хотите, чтобы источник выдерживал неправильное кодирование, вы можете экранировать строку в кодировке cp932:

puts "\x82\xb1\x82\xf1\x82\xc9\x82\xbf\x82\xcd\x81E\x8d\xa1\x93\xfa\x82\xcd"

Но если вы запустите его на машине в другой локали, он выдаст других персонажей. Вы не сможете записать японский язык на консоль по умолчанию из Ruby при установке в Windows (кодовая страница 1252).

(Хотя Ruby 1.9 значительно улучшает обработку Unicode, здесь он ничего не меняет. Это все еще приложение на основе байтов, использующее функции ввода-вывода стандартной библиотеки C, и это означает, что оно ограничено локальной кодовой страницей Windows.)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...