Преобразование целых чисел в UTF-8 (корейский) - PullRequest
0 голосов
/ 27 августа 2011

Я использую Ruby 1.9.2 и пытаюсь исправить какой-то неправильный ввод текста UTF-8, где текст буквально "\\354\\203\\201\\355\\221\\234\\353\\252\\205", и изменить его на правильный корейский "상표명"

Однако, после поисков и попыток нескольких методов, я все равно получаю тарабарщину. Это сбивает с толку, так как пример экранированных символов в строке 3 работает нормально

# encoding: utf-8
puts "상표명" # Target string
# Output: "상표명"

puts "\354\203\201\355\221\234\353\252\205" # Works with escaped characters like this
# Output: "상표명"

# Real input is a string
input = "\\354\\203\\201\\355\\221\\234\\353\\252\\205"

# After some manipulation got it into an array of numbers
puts [354, 203,201,355,221,234,353,252,205].pack('U*').force_encoding('UTF-8')
# Output: ŢËÉţÝêšüÍ (gibberish)

Я уверен, что на это где-то ответили, но мне не удалось его найти.

Ответы [ 2 ]

10 голосов
/ 27 августа 2011

Это то, что вы хотите сделать, чтобы получить текст на корейском языке UTF-8:

s = "\\354\\203\\201\\355\\221\\234\\353\\252\\205"
k = s.scan(/\d+/).map { |n| n.to_i(8) }.pack("C*").force_encoding('utf-8')
# "상표명"

И вот как это работает:

  1. Строка ввода хороша ирегулярный, поэтому мы можем использовать scan для извлечения индивидуального номера.
  2. Затем map с to_i(8) для преобразования восьмеричные значения (как отметил Хеннинг Махолм) в целые числа.
  3. Теперь нам нужно преобразовать наш список целых чисел в байты, чтобы мы pack('C*') получилистрока байтов.Эта строка будет иметь кодировку BINARY (AKA ASCII-8BIT).
  4. Мы знаем, что байты действительно представляют UTF-8, поэтому мы можем вызвать проблему с помощью force_encoding('utf-8').

Главное, чего вам не хватало - это ваш формат pack;'U' означает «символ UTF-8» и будет ожидать массив кодовых точек Unicode, каждая из которых представлена ​​одним целым числом, 'C' ожидает массив байтов, и это то, что у нас было.

2 голосов
/ 27 августа 2011

\354 и т. Д. восьмеричные экранированные, а не десятичные, поэтому вы не можете просто записать их как 354, чтобы получить целочисленные значения байтов.

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