Три занимался одной задачей. Накопилось у меня около 400 картинок с ресурса Historicana, названных неправильно. Каждая картинка - это описание исторического момента. Короче, решил добавить к .jpg комментарии и переименовать файло. Подумалось, что удобнее взять транслит. И понеслись злоключения.
Начнем с того, что готовая либа JPEG сделана через жопу. Например, с трудом скомпилированный wrjpgcom.c выплевывает в консоль данные, и получается не картинка, а мусор. Пострадал немного, плюнул и сел за код. По идее проще всего искать маркеры картинки, пропускать комментарий или, если он не найден, то вписывать до $FFDA. Наверняка криворукие кодеры обработают неверно. Наплевать, некоторые программы справляются корректно.
Написал код(prb.pb) и из 200 картинок получилось меньше. стал искать, в чем причина, нашел в отладочном логе. Причина в некорректном имени файла, некоторые буквы ё и й отображаются как unicode. Справился с 16ю неверными именами, осталось переводить имя в транслит.
Эта задача совпала с проектом, над которым я занимался. Только вышла unicode-версия, которая мне и помогла. Беру старые программы, добавляю текст и вместо имени в unicode вижу "???".
"Филипп, ты влип". Дописал код, который было лень доделывать, переименовал все файлы. Количество совпало, это радует. Осталось 300 картинок, к которым добавлены текстовые файлы, не знаю, что делать.
Короче, вернулся к транслиту и решил написать две функции на TinyC. Писал код с соплями и матом - я Си не знаю и кое-что не понимаю. Сделал улучшенный код транслита, но вынести код в функцию не удалось. И да и выполнение обратной функции детранслитерации превратилось бы в очередной кошмар разработки. Переписал заново и дополнил код. Теперь у меня есть готовая библиотека. Папка tcc - пример, tcc_lib - либа, перекомпилированная на lcc-win32.
Почему я взялся за этот геморрой? Вот пример, найденный в интернетах:
#include <stdio.h>
#include <conio.h>
#include "string.h"
void Transliterate(char* str, char* newStr)
{
for (; *str != 0; str++)
{
switch (str[0])
{
case 'а': strcat(&newStr[0], "a"); break;
case 'б': strcat(&newStr[0], "b"); break;
case 'в': strcat(&newStr[0], "v"); break;
case 'г': strcat(&newStr[0], "g"); break;
case 'д': strcat(&newStr[0], "d"); break;
case 'е': strcat(&newStr[0], "e"); break;
case 'ё': strcat(&newStr[0], "ye"); break;
case 'ж': strcat(&newStr[0], "zh"); break;
case 'з': strcat(&newStr[0], "z"); break;
case 'и': strcat(&newStr[0], "i"); break;
case 'й': strcat(&newStr[0], "y"); break;
case 'к': strcat(&newStr[0], "k"); break;
case 'л': strcat(&newStr[0], "l"); break;
case 'м': strcat(&newStr[0], "m"); break;
case 'н': strcat(&newStr[0], "n"); break;
case 'о': strcat(&newStr[0], "o"); break;
case 'п': strcat(&newStr[0], "p"); break;
case 'р': strcat(&newStr[0], "r"); break;
case 'с': strcat(&newStr[0], "s"); break;
case 'т': strcat(&newStr[0], "t"); break;
case 'у': strcat(&newStr[0], "u"); break;
case 'ф': strcat(&newStr[0], "f"); break;
case 'х': strcat(&newStr[0], "kh"); break;
case 'ц': strcat(&newStr[0], "tc"); break;
case 'ч': strcat(&newStr[0], "ch"); break;
case 'ш': strcat(&newStr[0], "sh"); break;
case 'щ': strcat(&newStr[0], "shch"); break;
case 'ъ': strcat(&newStr[0], "''"); break;
case 'ы': strcat(&newStr[0], "y"); break;
case 'ь': strcat(&newStr[0], "''"); break;
case 'э': strcat(&newStr[0], "e"); break;
case 'ю': strcat(&newStr[0], "iu"); break;
case 'я': strcat(&newStr[0], "ia"); break;
case 'А': strcat(&newStr[0], "A"); break;
case 'Б': strcat(&newStr[0], "B"); break;
case 'В': strcat(&newStr[0], "V"); break;
case 'Г': strcat(&newStr[0], "G"); break;
case 'Д': strcat(&newStr[0], "D"); break;
case 'Е': strcat(&newStr[0], "E"); break;
case 'Ё': strcat(&newStr[0], "Ye"); break;
case 'Ж': strcat(&newStr[0], "ZH"); break;
case 'З': strcat(&newStr[0], "Z"); break;
case 'И': strcat(&newStr[0], "I"); break;
case 'Й': strcat(&newStr[0], "Y"); break;
case 'К': strcat(&newStr[0], "K"); break;
case 'Л': strcat(&newStr[0], "L"); break;
case 'М': strcat(&newStr[0], "M"); break;
case 'Н': strcat(&newStr[0], "N"); break;
case 'О': strcat(&newStr[0], "O"); break;
case 'П': strcat(&newStr[0], "P"); break;
case 'Р': strcat(&newStr[0], "R"); break;
case 'С': strcat(&newStr[0], "S"); break;
case 'Т': strcat(&newStr[0], "T"); break;
case 'У': strcat(&newStr[0], "U"); break;
case 'Ф': strcat(&newStr[0], "F"); break;
case 'Х': strcat(&newStr[0], "Kh"); break;
case 'Ц': strcat(&newStr[0], "TC"); break;
case 'Ч': strcat(&newStr[0], "Ch"); break;
case 'Ш': strcat(&newStr[0], "Sh"); break;
case 'Щ': strcat(&newStr[0], "ShCh"); break;
case 'Ъ': strcat(&newStr[0], "''"); break;
case 'Ы': strcat(&newStr[0], "Y"); break;
case 'Ь': strcat(&newStr[0], "''"); break;
case 'Э': strcat(&newStr[0], "E"); break;
case 'Ю': strcat(&newStr[0], "IU"); break;
case 'Я': strcat(&newStr[0], "IA"); break;
default: { char Temp[2] = { str[0], 0} ; strcat(&newStr[0], &Temp[0]); }
}
}
}
int main()
{
char* x = "Привет мир!";
char y[100] = {0};
Transliterate(x, &y[0]);
printf("%s\n", y);
return 0;
}
Теперь о программе, над которой я работал.
В нее включена кодировка по ГОСТу, над другими я не работал. Надеюсь, что сделано верно, хотя над алгоритмом надо еще поработать.
Архив всех переделок.
Комментарии
Отправить комментарий