Javascript.RU

Создать новую тему Ответ
 
Опции темы Искать в теме
  #1 (permalink)  
Старый 26.12.2011, 17:01
Аватар для B~Vladi
Модератор Всея Форума
Отправить личное сообщение для B~Vladi Посмотреть профиль Найти все сообщения от B~Vladi
 
Регистрация: 14.05.2009
Сообщений: 4,021

Функция парсинга строки в массив байт.
Понадобилась мне такая функция, но в гугле я её не нашел. С помощью x-yuri мне удалось это сделать:

function parseStrToBuffer (string) {
  var result = [],
  index = 0,
  length = string.length,
  code;

  for (; index < length; index++) {
    code = string.charCodeAt(index);
    if (code <= 0x7f) {
      result.push(code);
    } else if (code <= 0x7ff) {
      result.push(code >>> 6 | 0xc0,
        code & 0x3f | 0x80);
    } else if (code <= 0xffff) {
      result.push(code >>> 12 | 0xe0,
        code >>> 6 & 0x3f | 0x80,
        code & 0x3f | 0x80);
    } else if (code <= 0x1fffff) {
      result.push(code >>> 18 | 0xf0,
        code >>> 12 & 0x3f | 0x80,
        code >>> 6 & 0x3f | 0x80,
        code & 0x3f | 0x80);
    } else if (code <= 0x3ffffff) {
      result.push(code >>> 24 | 0xf8,
        code >>> 18 & 0x3f | 0x80,
        code >>> 12 & 0x3f | 0x80,
        code >>> 6 & 0x3f | 0x80,
        code & 0x3f | 0x80);
    } else if (code <= 0x7fffffff) {
      result.push(code >>> 30 | 0xfc,
        code >>> 24 & 0x3f | 0x80,
        code >>> 18 & 0x3f | 0x80,
        code >>> 12 & 0x3f | 0x80,
        code >>> 6 & 0x3f | 0x80,
        code & 0x3f | 0x80);
    }
  }

  return result;
}

// Test string: ﻰﺠ﷼ﺒ╤Ή
// Result: [ 239, 187, 176, 239, 186, 160, 239, 183, 188, 239, 186, 146, 226, 149, 164, 206, 137 ]
alert(JSON.stringify(parseStrToBuffer(prompt('Enter string'))));


Функция эквивалентна вызову:
new Buffer('string', 'utf8');

в NodeJS.

Правила кодировки UTF8 брал отсюда.
__________________
Болтовня ничего не стоит. Покажите мне код. — Linus Torvalds
влад.куркин.рф

Последний раз редактировалось B~Vladi, 26.12.2011 в 18:23.
Ответить с цитированием
  #2 (permalink)  
Старый 26.12.2011, 17:38
Аватар для B@rmaley.e><e
⊞ Развернуть
Отправить личное сообщение для B@rmaley.e><e Посмотреть профиль Найти все сообщения от B@rmaley.e><e
 
Регистрация: 11.01.2010
Сообщений: 1,810

Сообщение от B~Vladi
в гугле я её не нашел
utf82str — не то?
Ответить с цитированием
  #3 (permalink)  
Старый 26.12.2011, 17:43
Аватар для nerv_
junior
Отправить личное сообщение для nerv_ Посмотреть профиль Найти все сообщения от nerv_
 
Регистрация: 29.11.2011
Сообщений: 3,924

B~Vladi, можете пояснить логику? Есть строка, разбираете по символам, узнаете код символа, а дальше что? Мне сама формулировка непонятна
Сообщение от B~Vladi
Функция парсинга строки в массив байт.
__________________
Чебурашка стал символом олимпийских игр. А чего достиг ты?
Тишина - самый громкий звук

Последний раз редактировалось nerv_, 26.12.2011 в 17:47.
Ответить с цитированием
  #4 (permalink)  
Старый 26.12.2011, 17:52
Аватар для Nekromancer
Профессор
Отправить личное сообщение для Nekromancer Посмотреть профиль Найти все сообщения от Nekromancer
 
Регистрация: 06.05.2009
Сообщений: 1,163

nerv_,
Код символа это ведь число. Число состоит из байт.
В utf8 специальная система кодирования, где один символ разбивается на несколько байт.
А получить массив байт, это получить все байты, просто разбить числа на составляющие.
В простонародье - создать буфер.
__________________
Нужно равняться на лучших, а не оправдываться за счёт худших.
Ответить с цитированием
  #5 (permalink)  
Старый 26.12.2011, 17:55
Аватар для nerv_
junior
Отправить личное сообщение для nerv_ Посмотреть профиль Найти все сообщения от nerv_
 
Регистрация: 29.11.2011
Сообщений: 3,924

Nekromancer, спасибо) Просто не понимаю, как после получения числа, отличного от 255 (если байт это от 0 до 255) или от или -128 до 127 (если байт это от -128 до 127) их записать в байты? Сбросить биты по маске? Тогда в чем смыл?
__________________
Чебурашка стал символом олимпийских игр. А чего достиг ты?
Тишина - самый громкий звук
Ответить с цитированием
  #6 (permalink)  
Старый 26.12.2011, 18:02
Аватар для B@rmaley.e><e
⊞ Развернуть
Отправить личное сообщение для B@rmaley.e><e Посмотреть профиль Найти все сообщения от B@rmaley.e><e
 
Регистрация: 11.01.2010
Сообщений: 1,810

Сообщение от nerv_
их записать в байты?
Тогда это будет не 1, а несколько байт. (А именно [log_256 n] + 1, где [] — округление с отбрасыванием дробной части, а n — число)
Ответить с цитированием
  #7 (permalink)  
Старый 26.12.2011, 18:05
Аватар для Nekromancer
Профессор
Отправить личное сообщение для Nekromancer Посмотреть профиль Найти все сообщения от Nekromancer
 
Регистрация: 06.05.2009
Сообщений: 1,163

Число в JavaScript это - doubleword (Двойное слово, 4 байта. Ну или uint32).
Каждый байт получается примерно так:
n & 0xFF
n >>> 8
// далее повторяются шаги, в идеале 4 раз
__________________
Нужно равняться на лучших, а не оправдываться за счёт худших.
Ответить с цитированием
  #8 (permalink)  
Старый 26.12.2011, 18:16
Аватар для B~Vladi
Модератор Всея Форума
Отправить личное сообщение для B~Vladi Посмотреть профиль Найти все сообщения от B~Vladi
 
Регистрация: 14.05.2009
Сообщений: 4,021

Сообщение от B@rmaley.e><e
utf82str — не то?
Ну вообще это реализация str2utf8. У них не учитываются 31-битные числа. За ссылку спасибо.

Сообщение от B@rmaley.e><e
Есть строка, разбираете по символам, узнаете код символа, а дальше что?
А дальше смотрим как кодировка UTF8 кодирует символы в байты. Это показано во второй таблице, по ссылке из первого поста.

Из этой таблице видно, что коды символов могут лежать в некоторых диапазонах. Допустим, если код символа меньше или равно 0x7ff, то символ кодируется одним байтом. Если больше, то несколькими (максимум 6 байт, последняя строка таблицы).

Рассмотрим символ ♫.
Его код 9835, или в бинарном представлении 00100110 01101011, т.е. 16 бит.
UTF8 кодирует 16-битные числа в трех байтах (см. табличку). Т.е. этот символ весит 3 байта, тогда как латинские буквы 1.

Смотрим на табличку:
1110xxxx 10xxxxxx 10xxxxxx

Здесь x - это 1 бит числа, которое мы хотим закодировать. Цифры - служебные биты.
Т.е. мы берём биты числа и раскладываем по нужным местам в соответствующем порядке:

11100010 10011001 10101011
Жирным выделены биты кода нашего символа. Собственно, этим и занимается ветка if(code <= 0xffff):
Сообщение от nerv_
Вижу битовые операторы, но логика их работы не понятна.
Берём нужные биты, двигаем на нужные места (в конец байта) и добавляем служебные в начало.

В итоге, мы получаем 3 байта (3 числа):
Первое: 11100010 - это 226 в десятичной системе.
Второе: 10011001 - это 153 в десятичной системе.
Третье: 10101011 - это 171 в десятичной системе.

Собственно, то что мы и наблюдаем в результирующем массиве.
__________________
Болтовня ничего не стоит. Покажите мне код. — Linus Torvalds
влад.куркин.рф
Ответить с цитированием
  #9 (permalink)  
Старый 26.12.2011, 18:20
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,105

B~Vladi,
this.push(code >>> 24 | 0xf8, это правильно?
Ответить с цитированием
  #10 (permalink)  
Старый 26.12.2011, 18:23
Аватар для B~Vladi
Модератор Всея Форума
Отправить личное сообщение для B~Vladi Посмотреть профиль Найти все сообщения от B~Vladi
 
Регистрация: 14.05.2009
Сообщений: 4,021

Сообщение от рони
this.push(code >>> 24 | 0xf8, это правильно?
Нет, конечно же, исправил. Спасибо, не заметил.
__________________
Болтовня ничего не стоит. Покажите мне код. — Linus Torvalds
влад.куркин.рф
Ответить с цитированием
Ответ



Опции темы Искать в теме
Искать в теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Разбиение строки на десятимерный массив cbone Общие вопросы Javascript 7 23.11.2011 08:15
Как создать многомерный массив FRIE Общие вопросы Javascript 29 02.06.2010 19:14
записать массив байт на сервер karabura AJAX и COMET 1 06.08.2009 05:21