IPB
ЛогинПароль:

> Потоковая конвертация между UTF-8 и UTF-32
сообщение
Сообщение #1


Большевик–концептуал
***

Группа: Пользователи
Сообщений: 194
Пол: Мужской
Реальное имя: Иван Левашев
Jabber: bu_gen@octagram.name
Skype: i.levashew
QQ: 3152538431
WeChat
Ада: Сторонник
Embarcadero Delphi: Сторонник
Free Pascal: Разработчик
Turbo Pascal: Установлен

Репутация: -  1  +


GNAT -gnat95

Выбранная тактика поддержки Юникода такова, что с системными файловыми API мы не морочимся, а вот с содержимым заморочиться можно и нужно. Уж байтики прочитанные-то понять надо суметь.

Требуется реализовать пассивный интерфейс конвертации туда и обратно по типу iconv. iconv принимает на вход буфер, на выход буфер, и сообщает позицию, где остановились чтение и запись. Также возвращается причина остановки. Реальный сишный iconv, если смотреть его API, ещё принимает размеры входного и выходного буфера, в нашем случае нужно полагаться на возможности языка Ада передавать длины массива и, если, допустим, из буфера нужно читать не сначала или в буфер писать не с начала, нарезать нужный кусочек массива синтаксисом Массив (Индекс .. Индекс).

ВАЖНО: всевозможные функции, возвращающие массивы, как правило, делают их с начальным индексом 1, но полагаться на это запрещено. Начинать перебирать любой массив нужно с 'First, причём, с правильного 'First, соответствующего массиву, а то я как раз в библиотеке GNAT где-то напоролся в конвертации UTF, что там 'First не от того массива берётся.

Под пассивностью подразумевается, что функция конвертации не выделяет память, а только пишет, куда ей дали.

У конвертации есть некоторое состояние. Я думаю, будет достаточно объявить type Conversion_UTF_32_To_UTF_8 is private; и type Conversion_UTF_8_To_UTF_32 is private;

Внутри состояние конечного автомата и недособранный 32битный символ, предпочтительно, Interfaces.Unsigned_32.

От реализации я бы очень хотел реализации разгона, когда оба буфера позволяют. В общем случае работа функции конвертации может происходить так:
  • побайтовая обработка
  • разгон
  • побайтовая обработка

На старте побайтовая обработка нужна, если состояние, в котором вызвали конвертацию, было не основным (готовность прочитать новый символ). В конце побайтовая обработка нужна, если ещё есть, что конвертировать во входном буфере, но пространство для манёвра во входном и выходном буферах не позволяет продолжать разгон. Может быть, его достаточно, но мы не знаем. Например, на входе один байт и на выходе место для одного 32битного символа, и байт оказался ASCII. Всё хорошо, но для разгона резерв недостаточен.

Чтобы разогнаться, нужно быть в основном состоянии и всё время разгона пребывать в нём, и чтобы на входе и выходе было пространство для любых возможных ситуаций. Например, при чтении UTF-8, чтобы поддерживать чтение суррогатных пар, закодированных в UTF-8, нужен резерв 6 октетов во входном буфере. А при записи, так как сейчас нам, кажется, не нужно писать в таком ублюдочном формате, хватит и 4 октетов в выходном буфере. На 32битные символы ограничения 1 штука. Но, правда, если на выходе уже нет места даже для одного 32битного символа, а на входе ещё есть байты, кажется правильным побайтово прочитать все байты, кроме последнего, наработав состояние.

Требуется поддержать:
валидный UTF-8 и валидный UTF-32
ничего сверх 17 стандартных плоскостей Юникода валидным не является
и также ситуацию, когда в UTF-8 закодированы две суррогатные пары, но только в таком виде

То есть, одиночные суррогатные пары — это не валидно.

BOM никакой особой обработки не требует. Если он встретился на входе, он как любой другой символ перетекает на выход.

Тип данных 32битных строк — String_32, который переименованный Wide_Wide_String. Октеты в Stream_Element_Array ожидаются.

Нужны тесты, которые по-всякому ровно и неровно по границам пихают данные корректные и некорректные.


--------------------
If you want to get to the top, you have to start at the bottom
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
 
 Ответить  Открыть новую тему 
Ответов
сообщение
Сообщение #2


Большевик–концептуал
***

Группа: Пользователи
Сообщений: 194
Пол: Мужской
Реальное имя: Иван Левашев
Jabber: bu_gen@octagram.name
Skype: i.levashew
QQ: 3152538431
WeChat
Ада: Сторонник
Embarcadero Delphi: Сторонник
Free Pascal: Разработчик
Turbo Pascal: Установлен

Репутация: -  1  +


Требуемый програмный интерфейс достаточно универсален, чтоб можно было закодировать поверх него и циклический буфер тоже. Если последний раз остановились где-то посередине, передаём срез в конце массива в конвертор. Потом передаём срез в начале массива в конвертор.


--------------------
If you want to get to the top, you have to start at the bottom
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #3


Новичок
*

Группа: Пользователи
Сообщений: 27
Пол: Мужской
Реальное имя: Сергей Дюков
Skype: sergey.dukov54
Ада: Разработчик
Компонентный Паскаль: Сторонник

Репутация: -  0  +


А не подскажете, есть ли сейчас в стандартной библиотеке АДы конвейеры FIFO?
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 

Сообщений в этой теме


 Ответить  Открыть новую тему 
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 





- Текстовая версия 28.03.2024 17:59
500Gb HDD, 6Gb RAM, 2 Cores, 7 EUR в месяц — такие хостинги правда бывают
Связь с администрацией: bu_gen в домене octagram.name